protected SceneObjectGroup RezSingleAttachmentFromInventoryInternal(
            IClientAPI remoteClient, UUID itemID, uint AttachmentPt)
        {
            IInventoryAccessModule invAccess = m_scene.RequestModuleInterface <IInventoryAccessModule>();

            if (invAccess != null)
            {
                SceneObjectGroup objatt = invAccess.RezObject(remoteClient,
                                                              itemID, Vector3.Zero, Vector3.Zero, UUID.Zero, (byte)1, true,
                                                              false, false, remoteClient.AgentId, true);

//                m_log.DebugFormat(
//                    "[ATTACHMENTS MODULE]: Retrieved single object {0} for attachment to {1} on point {2}",
//                    objatt.Name, remoteClient.Name, AttachmentPt);

                if (objatt != null)
                {
                    bool tainted = false;
                    if (AttachmentPt != 0 && AttachmentPt != objatt.GetAttachmentPoint())
                    {
                        tainted = true;
                    }

                    // This will throw if the attachment fails
                    try
                    {
                        AttachObject(remoteClient, objatt, AttachmentPt, false);
                    }
                    catch
                    {
                        // Make sure the object doesn't stick around and bail
                        m_scene.DeleteSceneObject(objatt, false);
                        return(null);
                    }

                    if (tainted)
                    {
                        objatt.HasGroupChanged = true;
                    }

                    // Fire after attach, so we don't get messy perms dialogs
                    // 4 == AttachedRez
                    objatt.CreateScriptInstances(0, true, m_scene.DefaultScriptEngine, 4);
                    objatt.ResumeScripts();

                    // Do this last so that event listeners have access to all the effects of the attachment
                    m_scene.EventManager.TriggerOnAttach(objatt.LocalId, itemID, remoteClient.AgentId);
                }
                else
                {
                    m_log.WarnFormat(
                        "[ATTACHMENTS MODULE]: Could not retrieve item {0} for attaching to avatar {1} at point {2}",
                        itemID, remoteClient.Name, AttachmentPt);
                }

                return(objatt);
            }

            return(null);
        }
Exemplo n.º 2
0
        /// <summary>
        /// Move the next object in the queue to inventory.  Then delete it properly from the scene.
        /// </summary>
        /// <returns></returns>
        public bool InventoryDeQueueAndDelete()
        {
            DeleteToInventoryHolder x = null;

            try
            {
                lock (m_inventoryDeletes)
                {
                    int left = m_inventoryDeletes.Count;
                    if (left > 0)
                    {
                        x = m_inventoryDeletes.Dequeue();

                        //                        m_log.DebugFormat(
                        //                            "[ASYNC DELETER]: Sending object to user's inventory, action {1}, count {2}, {0} item(s) remaining.",
                        //                            left, x.action, x.objectGroups.Count);

                        try
                        {
                            IInventoryAccessModule invAccess = m_scene.RequestModuleInterface <IInventoryAccessModule>();
                            if (invAccess != null)
                            {
                                invAccess.CopyToInventory(x.action, x.folderID, x.objectGroups, x.remoteClient, false);
                            }

                            if (x.permissionToDelete)
                            {
                                foreach (SceneObjectGroup g in x.objectGroups)
                                {
                                    m_scene.DeleteSceneObject(g, true);
                                }
                            }
                        }
                        catch (Exception e)
                        {
                            m_log.ErrorFormat(
                                "[ASYNC DELETER]: Exception background sending object: {0}{1}", e.Message, e.StackTrace);
                        }

                        return(true);
                    }
                }
            }
            catch (Exception e)
            {
                // We can't put the object group details in here since the root part may have disappeared (which is where these sit).
                // FIXME: This needs to be fixed.
                m_log.ErrorFormat(
                    "[ASYNC DELETER]: Queued sending of scene object to agent {0} {1} failed: {2} {3}",
                    (x != null ? x.remoteClient.Name : "unavailable"),
                    (x != null ? x.remoteClient.AgentId.ToString() : "unavailable"),
                    e.Message,
                    e.StackTrace);
            }

            //            m_log.Debug("[ASYNC DELETER]: No objects left in inventory send queue.");

            return(false);
        }
Exemplo n.º 3
0
        public bool DeleteObject()
        {
            DeleteToInventoryHolder x = null;

            try
            {
                if (m_removeFromSimQueue.TryDequeue(out x))
                {
                    MainConsole.Instance.DebugFormat(
                        "[SCENE]: Sending object to user's inventory, {0} item(s) remaining.",
                        m_removeFromSimQueue.Count);

                    if (x.permissionToTake)
                    {
                        try
                        {
                            IInventoryAccessModule invAccess = m_scene.RequestModuleInterface <IInventoryAccessModule>();
                            UUID itemID;
                            if (invAccess != null)
                            {
                                invAccess.DeleteToInventory(x.action, x.folderID, x.objectGroups, x.agentId, out itemID);
                            }
                        }
                        catch (Exception e)
                        {
                            MainConsole.Instance.ErrorFormat(
                                "[ASYNC DELETER]: Exception background sending object: {0}{1}", e.Message, e.StackTrace);
                        }
                    }

                    //Moved Delete To After Object Taken To Inventory. Prevents script variables not being updated before taken to inventory
                    if (x.permissionToDelete)
                    {
                        IBackupModule backup = m_scene.RequestModuleInterface <IBackupModule>();
                        if (backup != null)
                        {
                            backup.DeleteSceneObjects(x.objectGroups.ToArray(), true, true);
                        }
                    }
                    return(true);
                }
            }
            catch (Exception e)
            {
                // We can't put the object group details in here since the root part may have disappeared (which is where these sit).
                // FIXME: This needs to be fixed.
                MainConsole.Instance.ErrorFormat(
                    "[SCENE]: Queued sending of scene object to agent {0} {1} failed: {2}",
                    (x != null ? x.agentId.ToString() : "unavailable"),
                    (x != null ? x.agentId.ToString() : "unavailable"), e);
            }

            //MainConsole.Instance.Debug("[SCENE]: No objects left in delete queue.");
            return(false);
        }
        /// <summary>
        /// Move the next object in the queue to inventory.  Then delete it properly from the scene.
        /// </summary>
        /// <returns></returns>
        public void InventoryDeQueueAndDelete()
        {
            lock (m_threadLock)
            {
                IInventoryAccessModule invAccess = m_scene.RequestModuleInterface <IInventoryAccessModule>();
                if (invAccess == null)
                {
                    return;
                }

                int count = 0;
                while (m_inventoryDeletes.TryDequeue(out DeleteToInventoryHolder x))
                {
                    //  m_log.DebugFormat(
                    //  "[ASYNC DELETER]: Sending object to user's inventory, action {1}, count {2}, {0} item(s) remaining.",
                    //  left, x.action, x.objectGroups.Count);
                    try
                    {
                        invAccess.CopyToInventory(x.action, x.folderID, x.objectGroups, x.remoteClient, false);
                        if (x.permissionToDelete)
                        {
                            foreach (SceneObjectGroup g in x.objectGroups)
                            {
                                m_scene.DeleteSceneObject(g, true);
                            }
                        }

                        count += x.objectGroups.Count;
                        if (count > 256)
                        {
                            Thread.Sleep(50); // throttle
                            count = 0;
                        }
                    }
                    catch
                    // catch (Exception e)
                    {
                        //m_log.ErrorFormat(
                        //    "[ASYNC OBJECT DELETER]: Exception background sending object: {0}{1}", e.Message, e.StackTrace);
                    }
                }
                // m_log.Debug("[ASYNC DELETER]: No objects left in inventory send queue.");
                m_running = false;
            }
        }
Exemplo n.º 5
0
 public void RegionLoaded(Scene scene)
 {
     m_invAccessModule = m_scene.RequestModuleInterface<IInventoryAccessModule>();
 }
        private SceneObjectGroup RezSingleAttachmentFromInventoryInternal(
            IScenePresence sp, UUID itemID, UUID assetID, uint attachmentPt)
        {
            IInventoryAccessModule invAccess = m_scene.RequestModuleInterface <IInventoryAccessModule>();

            if (invAccess != null)
            {
                lock (sp.AttachmentsSyncLock)
                {
                    SceneObjectGroup objatt;

                    if (itemID != UUID.Zero)
                    {
                        objatt = invAccess.RezObject(sp.ControllingClient,
                                                     itemID, Vector3.Zero, Vector3.Zero, UUID.Zero, (byte)1, true,
                                                     false, false, sp.UUID, true);
                    }
                    else
                    {
                        objatt = invAccess.RezObject(sp.ControllingClient,
                                                     null, assetID, Vector3.Zero, Vector3.Zero, UUID.Zero, (byte)1, true,
                                                     false, false, sp.UUID, true);
                    }

                    //                m_log.DebugFormat(
                    //                    "[ATTACHMENTS MODULE]: Retrieved single object {0} for attachment to {1} on point {2}",
                    //                    objatt.Name, remoteClient.Name, AttachmentPt);

                    if (objatt != null)
                    {
                        // HasGroupChanged is being set from within RezObject.  Ideally it would be set by the caller.
                        objatt.HasGroupChanged = false;
                        bool tainted = false;
                        if (attachmentPt != 0 && attachmentPt != objatt.AttachmentPoint)
                        {
                            tainted = true;
                        }

                        // This will throw if the attachment fails
                        try
                        {
                            AttachObject(sp, objatt, attachmentPt, false);
                        }
                        catch (Exception e)
                        {
                            m_log.ErrorFormat(
                                "[ATTACHMENTS MODULE]: Failed to attach {0} {1} for {2}, exception {3}{4}",
                                objatt.Name, objatt.UUID, sp.Name, e.Message, e.StackTrace);

                            // Make sure the object doesn't stick around and bail
                            sp.RemoveAttachment(objatt);
                            m_scene.DeleteSceneObject(objatt, false);
                            return(null);
                        }

                        if (tainted)
                        {
                            objatt.HasGroupChanged = true;
                        }

                        // Fire after attach, so we don't get messy perms dialogs
                        // 4 == AttachedRez
                        objatt.CreateScriptInstances(0, true, m_scene.DefaultScriptEngine, 4);
                        objatt.ResumeScripts();

                        // Do this last so that event listeners have access to all the effects of the attachment
                        m_scene.EventManager.TriggerOnAttach(objatt.LocalId, itemID, sp.UUID);

                        return(objatt);
                    }
                    else
                    {
                        m_log.WarnFormat(
                            "[ATTACHMENTS MODULE]: Could not retrieve item {0} for attaching to avatar {1} at point {2}",
                            itemID, sp.Name, attachmentPt);
                    }
                }
            }

            return(null);
        }
Exemplo n.º 7
0
        /// <summary>
        ///     Attach the object to the avatar
        /// </summary>
        /// <param name="remoteClient">The client that is having the attachment done</param>
        /// <param name="localID">The localID (SceneObjectPart) that is being attached (for the attach script event)</param>
        /// <param name="group">The group (SceneObjectGroup) that is being attached</param>
        /// <param name="AttachmentPt">The point to where the attachment will go</param>
        /// <param name="assetID" />
        /// <param name="forceUpdatePrim">Force updating of the prim the next time the user attempts to deattach it</param>
        /// <param name="isTempAttach">Is a temporary attachment</param>
        protected void FindAttachmentPoint(IClientAPI remoteClient, uint localID, ISceneEntity group,
                                           int AttachmentPt, UUID assetID, bool forceUpdatePrim, bool isTempAttach)
        {
            //Make sure that we arn't over the limit of attachments
            ISceneEntity[] attachments = GetAttachmentsForAvatar(remoteClient.AgentId);
            if (attachments.Length + 1 > m_maxNumberOfAttachments)
            {
                //Too many
                remoteClient.SendAgentAlertMessage(
                    "You are wearing too many attachments. Take one off to attach this object", false);

                return;
            }
            Vector3 attachPos = group.GetAttachmentPos();
            bool    hasMultipleAttachmentsSet = (AttachmentPt & 0x7f) != 0 || AttachmentPt == 0;

            if (!m_allowMultipleAttachments)
            {
                hasMultipleAttachmentsSet = false;
            }
            AttachmentPt &= 0x7f; //Disable it! Its evil!

            //Did the attachment change position or attachment point?
            bool changedPositionPoint = false;

            // If the attachment point isn't the same as the one previously used
            // set it's offset position = 0 so that it appears on the attachment point
            // and not in a weird location somewhere unknown.
            //Simplier terms: the attachment point changed, set it to the default 0,0,0 location
            if (AttachmentPt != 0 && AttachmentPt != (group.GetAttachmentPoint() & 0x7f))
            {
                attachPos            = Vector3.Zero;
                changedPositionPoint = true;
            }
            else
            {
                // AttachmentPt 0 means the client chose to 'wear' the attachment.
                if (AttachmentPt == 0)
                {
                    // Check object for stored attachment point
                    AttachmentPt = group.GetSavedAttachmentPoint() & 0x7f;
                    attachPos    = group.GetAttachmentPos();
                }

                //Check state afterwards... use the newer GetSavedAttachmentPoint and Pos above first
                if (AttachmentPt == 0)
                {
                    // Check object for older stored attachment point
                    AttachmentPt = group.RootChild.Shape.State & 0x7f;
                }

                // if we still didn't find a suitable attachment point, force it to the default
                //This happens on the first time an avatar 'wears' an object
                if (AttachmentPt == 0)
                {
                    // Stick it on right hand with Zero Offset from the attachment point.
                    AttachmentPt = (int)AttachmentPoint.RightHand;
                    //Default location
                    attachPos            = Vector3.Zero;
                    changedPositionPoint = true;
                }
            }

            MainConsole.Instance.DebugFormat(
                "[ATTACHMENTS MODULE]: Retrieved single object {0} for attachment to {1} on point {2} localID {3}",
                group.Name, remoteClient.Name, AttachmentPt, group.LocalId);

            //Update where we are put
            group.SetAttachmentPoint((byte)AttachmentPt);
            //Fix the position with the one we found
            group.AbsolutePosition = attachPos;

            // Remove any previous attachments
            IScenePresence presence = m_scene.GetScenePresence(remoteClient.AgentId);

            if (presence == null)
            {
                return;
            }
            UUID itemID = UUID.Zero;

            //Check for multiple attachment bits and whether we should remove the old
            if (!hasMultipleAttachmentsSet)
            {
                foreach (ISceneEntity grp in attachments)
                {
                    if (grp.GetAttachmentPoint() == (byte)AttachmentPt)
                    {
                        itemID = grp.RootChild.FromUserInventoryItemID;
                        break;
                    }
                }
                if (itemID != UUID.Zero)
                {
                    DetachSingleAttachmentToInventory(itemID, remoteClient);
                }
            }
            itemID = group.RootChild.FromUserInventoryItemID;

            group.RootChild.AttachedAvatar = presence.UUID;

            List <ISceneChildEntity> parts = group.ChildrenEntities();

            foreach (ISceneChildEntity t in parts)
            {
                t.AttachedAvatar = presence.UUID;
            }

            if (group.RootChild.PhysActor != null)
            {
                m_scene.PhysicsScene.DeletePrim(group.RootChild.PhysActor);
                group.RootChild.PhysActor = null;
            }

            group.RootChild.AttachedPos  = attachPos;
            group.RootChild.IsAttachment = true;
            group.AbsolutePosition       = attachPos;

            group.RootChild.SetParentLocalId(presence.LocalId);
            group.SetAttachmentPoint(Convert.ToByte(AttachmentPt));

            // Killing it here will cause the client to deselect it
            // It then reappears on the avatar, deselected
            // through the full update below
            if (group.IsSelected)
            {
                foreach (ISceneChildEntity part in group.ChildrenEntities())
                {
                    part.CreateSelected = true;
                }
            }

            //NOTE: This MUST be here, otherwise we limit full updates during attachments when they are selected and it will block the first update.
            // So until that is changed, this MUST stay. The client will instantly reselect it, so this value doesn't stay borked for long.
            group.IsSelected = false;

            if (!isTempAttach)
            {
                if (itemID == UUID.Zero)
                {
                    //Delete the object inworld to inventory

                    List <ISceneEntity> groups = new List <ISceneEntity>(1)
                    {
                        group
                    };

                    IInventoryAccessModule inventoryAccess = m_scene.RequestModuleInterface <IInventoryAccessModule>();
                    if (inventoryAccess != null)
                    {
                        inventoryAccess.DeleteToInventory(DeRezAction.AcquireToUserInventory, UUID.Zero,
                                                          groups, remoteClient.AgentId, out itemID);
                    }
                }
                else
                {
                    //it came from an item, we need to start the scripts

                    // Fire after attach, so we don't get messy perms dialogs.
                    group.CreateScriptInstances(0, true, StateSource.AttachedRez, UUID.Zero, false);
                }

                if (UUID.Zero == itemID)
                {
                    MainConsole.Instance.Error(
                        "[ATTACHMENTS MODULE]: Unable to save attachment. Error inventory item ID.");
                    remoteClient.SendAgentAlertMessage(
                        "Unable to save attachment. Error inventory item ID.", false);
                    return;
                }

                // XXYY!!
                if (assetID == UUID.Zero)
                {
                    assetID = m_scene.InventoryService.GetItemAssetID(remoteClient.AgentId, itemID);
                    //Update the ItemID with the new item
                    group.SetFromItemID(itemID, assetID);
                }
            }
            else
            {
                // Fire after attach, so we don't get messy perms dialogs.
                group.CreateScriptInstances(0, true, StateSource.AttachedRez, UUID.Zero, false);
                group.RootChild.FromUserInventoryItemID = UUID.Zero;
            }

            AvatarAttachments attPlugin = presence.RequestModuleInterface <AvatarAttachments>();

            if (attPlugin != null)
            {
                attPlugin.AddAttachment(group);
                presence.SetAttachments(attPlugin.Get());
                if (!isTempAttach)
                {
                    IAvatarAppearanceModule appearance = presence.RequestModuleInterface <IAvatarAppearanceModule>();

                    appearance.Appearance.SetAttachments(attPlugin.Get());
                    AvatarFactory.QueueAppearanceSave(remoteClient.AgentId);
                }
            }


            // In case it is later dropped again, don't let
            // it get cleaned up
            group.RootChild.RemFlag(PrimFlags.TemporaryOnRez);
            group.HasGroupChanged = changedPositionPoint || forceUpdatePrim;
            //Now recreate it so that it is selected
            group.ScheduleGroupUpdate(PrimUpdateFlags.ForcedFullUpdate);

            m_scene.EventManager.TriggerOnAttach(localID, group.RootChild.FromUserInventoryItemID, remoteClient.AgentId);
        }
Exemplo n.º 8
0
        public ISceneEntity RezSingleAttachmentFromInventory(
            IClientAPI remoteClient, UUID itemID, UUID assetID, int AttachmentPt, bool updateUUIDs)
        {
            MainConsole.Instance.DebugFormat(
                "[ATTACHMENTS MODULE]: Rezzing attachment to point {0} from item {1} for {2}",
                (AttachmentPoint)AttachmentPt, itemID, remoteClient.Name);
            IInventoryAccessModule invAccess = m_scene.RequestModuleInterface <IInventoryAccessModule>();

            if (invAccess != null)
            {
                InventoryItemBase item   = null;
                ISceneEntity      objatt = assetID == UUID.Zero
                                          ? invAccess.CreateObjectFromInventory(remoteClient,
                                                                                itemID, out item)
                                          : invAccess.CreateObjectFromInventory(remoteClient, itemID, assetID, null);

                if (objatt != null)
                {
                    #region Set up object for attachment status

                    if (item != null)
                    {
                        assetID = item.AssetID;

                        // 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.
                        objatt.RootChild.Name        = item.Name;
                        objatt.RootChild.Description = item.Description;
                    }

                    objatt.RootChild.Flags       |= PrimFlags.Phantom;
                    objatt.RootChild.IsAttachment = true;
                    objatt.SetFromItemID(itemID, assetID);

                    List <ISceneChildEntity> partList = new List <ISceneChildEntity>(objatt.ChildrenEntities());

                    foreach (ISceneChildEntity part in partList)
                    {
                        part.AttachedAvatar = remoteClient.AgentId;
                    }

                    objatt.SetGroup(remoteClient.ActiveGroupId, remoteClient.AgentId, false);
                    if (objatt.RootChild.OwnerID != remoteClient.AgentId)
                    {
                        //Need to kill the for sale here
                        objatt.RootChild.ObjectSaleType = 0;
                        objatt.RootChild.SalePrice      = 10;

                        if (m_scene.Permissions.PropagatePermissions())
                        {
                            if (item == null)
                            {
                                item = m_scene.InventoryService.GetItem(remoteClient.AgentId, itemID);
                            }
                            if (item == null)
                            {
                                return(null);
                            }
                            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
                                }
                            }

                            objatt.ApplyNextOwnerPermissions();
                        }
                    }

                    foreach (ISceneChildEntity part in partList)
                    {
                        if (part.OwnerID != remoteClient.AgentId)
                        {
                            part.LastOwnerID = part.OwnerID;
                            part.OwnerID     = remoteClient.AgentId;
                            part.Inventory.ChangeInventoryOwner(remoteClient.AgentId);
                        }
                    }
                    objatt.RootChild.TrimPermissions();
                    objatt.RootChild.IsAttachment = true;
                    objatt.IsDeleted = false;

                    //Update the ItemID with the new item
                    objatt.SetFromItemID(itemID, assetID);

                    //We also have to reset the IDs so that it doesn't have the same IDs as one inworld (possibly)!
                    ISceneEntity[] atts = GetAttachmentsForAvatar(remoteClient.AgentId);
                    foreach (var obj in atts)
                    {
                        if (obj.UUID == objatt.UUID)
                        {
                            updateUUIDs = false; //If the user is already wearing it, don't readd
                        }
                    }
                    bool forceUpdateOnNextDeattach = false;
                    try
                    {
                        bool foundDuplicate = false;
                        foreach (var obj in atts)
                        {
                            if (obj.RootChild.FromUserInventoryItemID == objatt.RootChild.FromUserInventoryItemID)
                            {
                                foundDuplicate = true;
                            }
                        }
                        IEntity e;
                        if (!m_scene.SceneGraph.TryGetEntity(objatt.UUID, out e)) //if (updateUUIDs)
                        {
                            foreach (var prim in objatt.ChildrenEntities())
                            {
                                prim.LocalId = 0;
                            }
                            bool success = m_scene.SceneGraph.RestorePrimToScene(objatt, false);
                            if (!success)
                            {
                                MainConsole.Instance.Error("[AttachmentModule]: Failed to add attachment " + objatt.Name +
                                                           " for user " + remoteClient.Name + "!");
                                return(null);
                            }
                        }
                        else
                        {
                            if (!foundDuplicate)
                            {
                                //If the user has information stored about this object, we need to force updating next time
                                if (m_scene.SceneGraph.AddPrimToScene(objatt))
                                {
                                    forceUpdateOnNextDeattach = true;
                                }
                            }
                            else
                            {
                                if (e as ISceneEntity != null)
                                {
                                    (e as ISceneEntity).ScheduleGroupUpdate(PrimUpdateFlags.ForcedFullUpdate);
                                }

                                return(e as ISceneEntity);  //It was already added
                            }
                        }
                    }
                    catch
                    {
                    }

                    //If we updated the attachment, we need to save the change
                    IScenePresence presence = m_scene.GetScenePresence(remoteClient.AgentId);
                    if (presence != null)
                    {
                        FindAttachmentPoint(remoteClient, objatt.LocalId, objatt, AttachmentPt, assetID,
                                            forceUpdateOnNextDeattach, false);
                    }
                    else
                    {
                        objatt = null; //Presence left, kill the attachment
                    }
                    #endregion
                }
                else
                {
                    MainConsole.Instance.WarnFormat(
                        "[ATTACHMENTS MODULE]: Could not retrieve item {0} for attaching to avatar {1} at point {2}",
                        itemID, remoteClient.Name, AttachmentPt);
                }

                return(objatt);
            }

            return(null);
        }
Exemplo n.º 9
0
 public void RegionLoaded(Scene scene)
 {
     m_invAccessModule = m_scene.RequestModuleInterface <IInventoryAccessModule>();
 }
Exemplo n.º 10
0
        public ISceneEntity RezSingleAttachmentFromInventory(
            IClientAPI remoteClient, UUID itemID, int AttachmentPt)
        {
            m_log.DebugFormat(
                "[ATTACHMENTS MODULE]: Rezzing attachment to point {0} from item {1} for {2}",
                (AttachmentPoint)AttachmentPt, itemID, remoteClient.Name);
            IInventoryAccessModule invAccess = m_scene.RequestModuleInterface <IInventoryAccessModule>();

            if (invAccess != null)
            {
                SceneObjectGroup objatt = invAccess.CreateObjectFromInventory(remoteClient,
                                                                              itemID);

                if (objatt != null)
                {
                    #region Set up object for attachment status

                    InventoryItemBase item = new InventoryItemBase(itemID, remoteClient.AgentId);
                    item = m_scene.InventoryService.GetItem(item);

                    objatt.RootPart.Flags       |= PrimFlags.Phantom;
                    objatt.RootPart.IsAttachment = true;
                    objatt.SetFromItemID(itemID);

                    // 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.
                    objatt.RootPart.Name        = item.Name;
                    objatt.RootPart.Description = item.Description;

                    List <SceneObjectPart> partList = new List <SceneObjectPart>(objatt.ChildrenList);

                    objatt.SetGroup(remoteClient.ActiveGroupId, remoteClient);
                    if (objatt.RootPart.OwnerID != item.Owner)
                    {
                        //Need to kill the for sale here
                        objatt.RootPart.ObjectSaleType = 0;
                        objatt.RootPart.SalePrice      = 10;

                        if (m_scene.Permissions.PropagatePermissions())
                        {
                            if ((item.CurrentPermissions & 8) != 0)
                            {
                                foreach (SceneObjectPart part in partList)
                                {
                                    part.EveryoneMask  = item.EveryOnePermissions;
                                    part.NextOwnerMask = item.NextPermissions;
                                    part.GroupMask     = 0; // DO NOT propagate here
                                }
                            }

                            objatt.ApplyNextOwnerPermissions();
                        }
                    }

                    foreach (SceneObjectPart part in partList)
                    {
                        if (part.OwnerID != item.Owner)
                        {
                            part.LastOwnerID = part.OwnerID;
                            part.OwnerID     = item.Owner;
                            part.Inventory.ChangeInventoryOwner(item.Owner);
                        }
                    }
                    objatt.RootPart.TrimPermissions();
                    objatt.RootPart.IsAttachment = true;
                    objatt.IsDeleted             = false;

                    //NOTE: we MUST do this manually, otherwise it will never be added!
                    //We also have to reset the IDs!
                    //Note: root first, as we have to set the parentID right!
                    m_scene.SceneGraph.PrepPrimForAdditionToScene(objatt);
                    m_scene.Entities.Add(objatt);

                    #endregion

                    //                m_log.DebugFormat(
                    //                    "[ATTACHMENTS MODULE]: Retrieved single object {0} for attachment to {1} on point {2}",
                    //                    objatt.Name, remoteClient.Name, AttachmentPt);

                    FindAttachmentPoint(remoteClient, objatt.LocalId, objatt, AttachmentPt, item);
                }
                else
                {
                    m_log.WarnFormat(
                        "[ATTACHMENTS MODULE]: Could not retrieve item {0} for attaching to avatar {1} at point {2}",
                        itemID, remoteClient.Name, AttachmentPt);
                }

                return(objatt);
            }

            return(null);
        }
Exemplo n.º 11
0
        public ISceneEntity RezSingleAttachmentFromInventory(
            IClientAPI remoteClient, UUID itemID, int AttachmentPt)
        {
            MainConsole.Instance.DebugFormat(
                "[ATTACHMENTS MODULE]: Rezzing attachment to point {0} from item {1} for {2}",
                (AttachmentPoint)AttachmentPt, itemID, remoteClient.Name);
            IInventoryAccessModule invAccess = m_scene.RequestModuleInterface <IInventoryAccessModule>();

            if (invAccess != null)
            {
                SceneObjectGroup objatt = invAccess.CreateObjectFromInventory(remoteClient,
                                                                              itemID);

                if (objatt != null)
                {
                    #region Set up object for attachment status

                    InventoryItemBase item = new InventoryItemBase(itemID, remoteClient.AgentId);
                    item = m_scene.InventoryService.GetItem(item);
                    if (item == null)
                    {
                        return(null);
                    }

                    objatt.RootPart.Flags       |= PrimFlags.Phantom;
                    objatt.RootPart.IsAttachment = true;
                    objatt.SetFromItemID(itemID, item.AssetID);

                    // 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.
                    objatt.RootPart.Name        = item.Name;
                    objatt.RootPart.Description = item.Description;

                    List <SceneObjectPart> partList = new List <SceneObjectPart>(objatt.ChildrenList);

                    foreach (SceneObjectPart part in partList)
                    {
                        part.AttachedAvatar = remoteClient.AgentId;
                    }

                    objatt.SetGroup(remoteClient.ActiveGroupId, remoteClient.AgentId);
                    if (objatt.RootPart.OwnerID != item.Owner)
                    {
                        //Need to kill the for sale here
                        objatt.RootPart.ObjectSaleType = 0;
                        objatt.RootPart.SalePrice      = 10;

                        if (m_scene.Permissions.PropagatePermissions())
                        {
                            if ((item.CurrentPermissions & 8) != 0)
                            {
                                foreach (SceneObjectPart part in partList)
                                {
                                    part.EveryoneMask  = item.EveryOnePermissions;
                                    part.NextOwnerMask = item.NextPermissions;
                                    part.GroupMask     = 0; // DO NOT propagate here
                                }
                            }

                            objatt.ApplyNextOwnerPermissions();
                        }
                    }

                    foreach (SceneObjectPart part in partList)
                    {
                        if (part.OwnerID != item.Owner)
                        {
                            part.LastOwnerID = part.OwnerID;
                            part.OwnerID     = item.Owner;
                            part.Inventory.ChangeInventoryOwner(item.Owner);
                        }
                    }
                    objatt.RootPart.TrimPermissions();
                    objatt.RootPart.IsAttachment = true;
                    objatt.IsDeleted             = false;

                    //Update the ItemID with the new item
                    objatt.SetFromItemID(itemID, item.AssetID);

                    //DO NOT SEND THIS KILL ENTITY
                    // If we send this, when someone copies an inworld object, then wears it, the inworld objects disapepars
                    // If a bug is caused by this, we need to figure out some other workaround.
                    //SendKillEntity(objatt.RootChild);
                    //We also have to reset the IDs so that it doesn't have the same IDs as one inworld (possibly)!
                    m_scene.SceneGraph.PrepPrimForAdditionToScene(objatt);
                    m_scene.Entities.Add(objatt);

                    //If we updated the attachment, we need to save the change
                    IScenePresence presence = m_scene.GetScenePresence(remoteClient.AgentId);
                    if (presence != null)
                    {
                        IAvatarAppearanceModule appearance = presence.RequestModuleInterface <IAvatarAppearanceModule>();
                        AvatarAttachments       attPlugin  = presence.RequestModuleInterface <AvatarAttachments>();
                        bool save = appearance.Appearance.CheckWhetherAttachmentChanged(AttachmentPt, item.ID, item.AssetID);
                        attPlugin.AddAttachment(objatt);
                        appearance.Appearance.SetAttachments(attPlugin.Get());
                        if (save)
                        {
                            AvatarFactory.QueueAppearanceSave(remoteClient.AgentId);
                        }

                        MainConsole.Instance.InfoFormat(
                            "[ATTACHMENTS MODULE]: Retrieved single object {0} for attachment to {1} on point {2} localID {3}",
                            objatt.Name, remoteClient.Name, AttachmentPt, objatt.LocalId);

                        FindAttachmentPoint(remoteClient, objatt.LocalId, objatt, AttachmentPt, item);
                    }
                    else
                    {
                        objatt = null;//Presence left, kill the attachment
                    }
                    #endregion
                }
                else
                {
                    MainConsole.Instance.WarnFormat(
                        "[ATTACHMENTS MODULE]: Could not retrieve item {0} for attaching to avatar {1} at point {2}",
                        itemID, remoteClient.Name, AttachmentPt);
                }

                return(objatt);
            }

            return(null);
        }