diff options
author | Melanie | 2010-10-07 05:12:39 +0200 |
---|---|---|
committer | Melanie | 2010-10-07 05:12:39 +0200 |
commit | ba0afa53d30566381d5757fb5a7b1ce55fe4521a (patch) | |
tree | 39c9ec1fb9beb8d3cc0c442b56026d3a62ca441b | |
parent | Implement taking of coalesced objects. (diff) | |
download | opensim-SC_OLD-ba0afa53d30566381d5757fb5a7b1ce55fe4521a.zip opensim-SC_OLD-ba0afa53d30566381d5757fb5a7b1ce55fe4521a.tar.gz opensim-SC_OLD-ba0afa53d30566381d5757fb5a7b1ce55fe4521a.tar.bz2 opensim-SC_OLD-ba0afa53d30566381d5757fb5a7b1ce55fe4521a.tar.xz |
Implement rezzing coalesced objects
-rw-r--r-- | OpenSim/Region/CoreModules/Framework/InventoryAccess/InventoryAccessModule.cs | 318 |
1 files changed, 182 insertions, 136 deletions
diff --git a/OpenSim/Region/CoreModules/Framework/InventoryAccess/InventoryAccessModule.cs b/OpenSim/Region/CoreModules/Framework/InventoryAccess/InventoryAccessModule.cs index 753aada..d429979 100644 --- a/OpenSim/Region/CoreModules/Framework/InventoryAccess/InventoryAccessModule.cs +++ b/OpenSim/Region/CoreModules/Framework/InventoryAccess/InventoryAccessModule.cs | |||
@@ -444,7 +444,14 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess | |||
444 | item.Folder = folder.ID; | 444 | item.Folder = folder.ID; |
445 | item.Owner = userID; | 445 | item.Owner = userID; |
446 | if (objlist.Count > 1) | 446 | if (objlist.Count > 1) |
447 | { | ||
447 | item.Flags = (uint)InventoryItemFlags.ObjectHasMultipleItems; | 448 | item.Flags = (uint)InventoryItemFlags.ObjectHasMultipleItems; |
449 | } | ||
450 | else | ||
451 | { | ||
452 | item.SaleType = objlist[0].RootPart.ObjectSaleType; | ||
453 | item.SalePrice = objlist[0].RootPart.SalePrice; | ||
454 | } | ||
448 | } | 455 | } |
449 | 456 | ||
450 | AssetBase asset = CreateAsset( | 457 | AssetBase asset = CreateAsset( |
@@ -508,7 +515,6 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess | |||
508 | 7); // Preserve folded permissions | 515 | 7); // Preserve folded permissions |
509 | } | 516 | } |
510 | 517 | ||
511 | // TODO: add the new fields (Flags, Sale info, etc) | ||
512 | item.CreationDate = Util.UnixTimeSinceEpoch(); | 518 | item.CreationDate = Util.UnixTimeSinceEpoch(); |
513 | item.Description = asset.Description; | 519 | item.Description = asset.Description; |
514 | item.Name = asset.Name; | 520 | item.Name = asset.Name; |
@@ -587,6 +593,8 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess | |||
587 | 593 | ||
588 | AssetBase rezAsset = m_Scene.AssetService.Get(item.AssetID.ToString()); | 594 | AssetBase rezAsset = m_Scene.AssetService.Get(item.AssetID.ToString()); |
589 | 595 | ||
596 | SceneObjectGroup group = null; | ||
597 | |||
590 | if (rezAsset != null) | 598 | if (rezAsset != null) |
591 | { | 599 | { |
592 | UUID itemId = UUID.Zero; | 600 | UUID itemId = UUID.Zero; |
@@ -595,16 +603,18 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess | |||
595 | // item that it came from. This allows us to enable 'save object to inventory' | 603 | // item that it came from. This allows us to enable 'save object to inventory' |
596 | if (!m_Scene.Permissions.BypassPermissions()) | 604 | if (!m_Scene.Permissions.BypassPermissions()) |
597 | { | 605 | { |
598 | if ((item.CurrentPermissions & (uint)PermissionMask.Copy) == (uint)PermissionMask.Copy) | 606 | if ((item.CurrentPermissions & (uint)PermissionMask.Copy) == (uint)PermissionMask.Copy && (item.Flags & (uint)InventoryItemFlags.ObjectHasMultipleItems) == 0) |
599 | { | 607 | { |
600 | itemId = item.ID; | 608 | itemId = item.ID; |
601 | } | 609 | } |
602 | } | 610 | } |
603 | else | 611 | else |
604 | { | 612 | { |
605 | // Brave new fullperm world | 613 | if ((item.Flags & (uint)InventoryItemFlags.ObjectHasMultipleItems) == 0) |
606 | // | 614 | { |
607 | itemId = item.ID; | 615 | // Brave new fullperm world |
616 | itemId = item.ID; | ||
617 | } | ||
608 | } | 618 | } |
609 | 619 | ||
610 | if (item.ID == UUID.Zero) | 620 | if (item.ID == UUID.Zero) |
@@ -613,27 +623,63 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess | |||
613 | } | 623 | } |
614 | 624 | ||
615 | string xmlData = Utils.BytesToString(rezAsset.Data); | 625 | string xmlData = Utils.BytesToString(rezAsset.Data); |
616 | SceneObjectGroup group | 626 | List<SceneObjectGroup> objlist = |
617 | = SceneObjectSerializer.FromOriginalXmlFormat(itemId, xmlData); | 627 | new List<SceneObjectGroup>(); |
618 | Vector3 storedPosition = group.AbsolutePosition; | 628 | List<Vector3> veclist = new List<Vector3>(); |
619 | if (group.UUID == UUID.Zero) | 629 | |
630 | XmlDocument doc = new XmlDocument(); | ||
631 | doc.LoadXml(xmlData); | ||
632 | XmlElement e = (XmlElement)doc.SelectSingleNode("/CoalescedObject"); | ||
633 | if (e == null || attachment) // Single | ||
620 | { | 634 | { |
621 | m_log.Debug("[InventoryAccessModule]: Inventory object has UUID.Zero! Position 3"); | 635 | SceneObjectGroup g = |
622 | } | 636 | SceneObjectSerializer.FromOriginalXmlFormat( |
623 | group.RootPart.FromFolderID = item.Folder; | 637 | itemId, xmlData); |
638 | objlist.Add(g); | ||
639 | veclist.Add(new Vector3(0, 0, 0)); | ||
624 | 640 | ||
625 | // If it's rezzed in world, select it. Much easier to | 641 | float offsetHeight = 0; |
626 | // find small items. | 642 | pos = m_Scene.GetNewRezLocation( |
627 | // | 643 | RayStart, RayEnd, RayTargetID, Quaternion.Identity, |
628 | if (!attachment) | 644 | BypassRayCast, bRayEndIsIntersection, true, g.GetAxisAlignedBoundingBox(out offsetHeight), false); |
645 | pos.Z += offsetHeight; | ||
646 | } | ||
647 | else | ||
629 | { | 648 | { |
630 | group.RootPart.CreateSelected = true; | 649 | XmlElement coll = (XmlElement)e; |
631 | foreach (SceneObjectPart child in group.Parts) | 650 | float bx = Convert.ToSingle(coll.GetAttribute("x")); |
632 | child.CreateSelected = true; | 651 | float by = Convert.ToSingle(coll.GetAttribute("y")); |
652 | float bz = Convert.ToSingle(coll.GetAttribute("z")); | ||
653 | Vector3 bbox = new Vector3(bx, by, bz); | ||
654 | |||
655 | pos = m_Scene.GetNewRezLocation(RayStart, RayEnd, | ||
656 | RayTargetID, Quaternion.Identity, | ||
657 | BypassRayCast, bRayEndIsIntersection, true, | ||
658 | bbox, false); | ||
659 | |||
660 | pos -= bbox / 2; | ||
661 | |||
662 | XmlNodeList groups = e.SelectNodes("SceneObjectGroup"); | ||
663 | foreach (XmlNode n in groups) | ||
664 | { | ||
665 | SceneObjectGroup g = | ||
666 | SceneObjectSerializer.FromOriginalXmlFormat( | ||
667 | itemId, n.OuterXml); | ||
668 | objlist.Add(g); | ||
669 | XmlElement el = (XmlElement)n; | ||
670 | float x = Convert.ToSingle(el.GetAttribute("offsetx")); | ||
671 | float y = Convert.ToSingle(el.GetAttribute("offsety")); | ||
672 | float z = Convert.ToSingle(el.GetAttribute("offsetz")); | ||
673 | veclist.Add(new Vector3(x, y, z)); | ||
674 | } | ||
633 | } | 675 | } |
634 | 676 | ||
677 | int primcount = 0; | ||
678 | foreach (SceneObjectGroup g in objlist) | ||
679 | primcount += g.PrimCount; | ||
680 | |||
635 | if (!m_Scene.Permissions.CanRezObject( | 681 | if (!m_Scene.Permissions.CanRezObject( |
636 | group.PrimCount, remoteClient.AgentId, pos) | 682 | primcount, remoteClient.AgentId, pos) |
637 | && !attachment) | 683 | && !attachment) |
638 | { | 684 | { |
639 | // The client operates in no fail mode. It will | 685 | // The client operates in no fail mode. It will |
@@ -645,135 +691,139 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess | |||
645 | remoteClient.SendBulkUpdateInventory(item); | 691 | remoteClient.SendBulkUpdateInventory(item); |
646 | return null; | 692 | return null; |
647 | } | 693 | } |
648 | if (group.UUID == UUID.Zero) | 694 | |
649 | { | 695 | for (int i = 0 ; i < objlist.Count ; i++ ) |
650 | m_log.Debug("[InventoryAccessModule]: Inventory object has UUID.Zero! Position 4"); | ||
651 | } | ||
652 | group.ResetIDs(); | ||
653 | if (group.UUID == UUID.Zero) | ||
654 | { | ||
655 | m_log.Debug("[InventoryAccessModule]: Inventory object has UUID.Zero! Position 5"); | ||
656 | } | ||
657 | if (attachment) | ||
658 | { | 696 | { |
659 | group.RootPart.Flags |= PrimFlags.Phantom; | 697 | group = objlist[i]; |
660 | group.RootPart.IsAttachment = true; | ||
661 | } | ||
662 | 698 | ||
663 | // If we're rezzing an attachment then don't ask AddNewSceneObject() to update the client since | 699 | Vector3 storedPosition = group.AbsolutePosition; |
664 | // we'll be doing that later on. Scheduling more than one full update during the attachment | 700 | if (group.UUID == UUID.Zero) |
665 | // process causes some clients to fail to display the attachment properly. | 701 | { |
666 | m_Scene.AddNewSceneObject(group, true, false); | 702 | m_log.Debug("[InventoryAccessModule]: Inventory object has UUID.Zero! Position 3"); |
703 | } | ||
704 | group.RootPart.FromFolderID = item.Folder; | ||
667 | 705 | ||
668 | // m_log.InfoFormat("ray end point for inventory rezz is {0} {1} {2} ", RayEnd.X, RayEnd.Y, RayEnd.Z); | 706 | // If it's rezzed in world, select it. Much easier to |
669 | // if attachment we set it's asset id so object updates can reflect that | 707 | // find small items. |
670 | // if not, we set it's position in world. | 708 | // |
671 | if (!attachment) | 709 | if (!attachment) |
672 | { | 710 | { |
673 | group.ScheduleGroupForFullUpdate(); | 711 | group.RootPart.CreateSelected = true; |
674 | 712 | foreach (SceneObjectPart child in group.Parts) | |
675 | float offsetHeight = 0; | 713 | child.CreateSelected = true; |
676 | pos = m_Scene.GetNewRezLocation( | 714 | } |
677 | RayStart, RayEnd, RayTargetID, Quaternion.Identity, | ||
678 | BypassRayCast, bRayEndIsIntersection, true, group.GetAxisAlignedBoundingBox(out offsetHeight), false); | ||
679 | pos.Z += offsetHeight; | ||
680 | group.AbsolutePosition = pos; | ||
681 | // m_log.InfoFormat("rezx point for inventory rezz is {0} {1} {2} and offsetheight was {3}", pos.X, pos.Y, pos.Z, offsetHeight); | ||
682 | 715 | ||
683 | } | 716 | group.ResetIDs(); |
684 | else | ||
685 | { | ||
686 | group.SetFromItemID(itemID); | ||
687 | } | ||
688 | if (group.UUID == UUID.Zero) | ||
689 | { | ||
690 | m_log.Debug("[InventoryAccessModule]: Inventory object has UUID.Zero! Position 6"); | ||
691 | } | ||
692 | SceneObjectPart rootPart = null; | ||
693 | try | ||
694 | { | ||
695 | rootPart = group.GetChildPart(group.UUID); | ||
696 | } | ||
697 | catch (NullReferenceException) | ||
698 | { | ||
699 | string isAttachment = ""; | ||
700 | 717 | ||
701 | if (attachment) | 718 | if (attachment) |
702 | isAttachment = " Object was an attachment"; | 719 | { |
720 | group.RootPart.Flags |= PrimFlags.Phantom; | ||
721 | group.RootPart.IsAttachment = true; | ||
722 | } | ||
703 | 723 | ||
704 | m_log.Error("[AGENT INVENTORY]: Error rezzing ItemID: " + itemID + " object has no rootpart." + isAttachment); | 724 | // If we're rezzing an attachment then don't ask |
705 | } | 725 | // AddNewSceneObject() to update the client since |
706 | if (group.UUID == UUID.Zero) | 726 | // we'll be doing that later on. Scheduling more than |
707 | { | 727 | // one full update during the attachment |
708 | m_log.Debug("[InventoryAccessModule]: Inventory object has UUID.Zero! Position 7"); | 728 | // process causes some clients to fail to display the |
709 | } | 729 | // attachment properly. |
710 | // Since renaming the item in the inventory does not affect the name stored | 730 | m_Scene.AddNewSceneObject(group, true, false); |
711 | // in the serialization, transfer the correct name from the inventory to the | 731 | |
712 | // object itself before we rez. | 732 | // if attachment we set it's asset id so object updates |
713 | rootPart.Name = item.Name; | 733 | // can reflect that, if not, we set it's position in world. |
714 | rootPart.Description = item.Description; | 734 | if (!attachment) |
715 | 735 | { | |
716 | group.SetGroup(remoteClient.ActiveGroupId, remoteClient); | 736 | group.ScheduleGroupForFullUpdate(); |
717 | if ((rootPart.OwnerID != item.Owner) || (item.CurrentPermissions & 16) != 0) | 737 | |
718 | { | 738 | group.AbsolutePosition = pos + veclist[i]; |
719 | //Need to kill the for sale here | 739 | } |
720 | rootPart.ObjectSaleType = 0; | 740 | else |
721 | rootPart.SalePrice = 10; | 741 | { |
742 | group.SetFromItemID(itemID); | ||
743 | } | ||
744 | |||
745 | SceneObjectPart rootPart = null; | ||
746 | |||
747 | try | ||
748 | { | ||
749 | rootPart = group.GetChildPart(group.UUID); | ||
750 | } | ||
751 | catch (NullReferenceException) | ||
752 | { | ||
753 | string isAttachment = ""; | ||
754 | |||
755 | if (attachment) | ||
756 | isAttachment = " Object was an attachment"; | ||
757 | |||
758 | m_log.Error("[AGENT INVENTORY]: Error rezzing ItemID: " + itemID + " object has no rootpart." + isAttachment); | ||
759 | } | ||
722 | 760 | ||
723 | if (m_Scene.Permissions.PropagatePermissions()) | 761 | // Since renaming the item in the inventory does not |
762 | // affect the name stored in the serialization, transfer | ||
763 | // the correct name from the inventory to the | ||
764 | // object itself before we rez. | ||
765 | rootPart.Name = item.Name; | ||
766 | rootPart.Description = item.Description; | ||
767 | rootPart.ObjectSaleType = item.SaleType; | ||
768 | rootPart.SalePrice = item.SalePrice; | ||
769 | |||
770 | group.SetGroup(remoteClient.ActiveGroupId, remoteClient); | ||
771 | if ((rootPart.OwnerID != item.Owner) || | ||
772 | (item.CurrentPermissions & 16) != 0) | ||
724 | { | 773 | { |
725 | foreach (SceneObjectPart part in group.Parts) | 774 | //Need to kill the for sale here |
775 | rootPart.ObjectSaleType = 0; | ||
776 | rootPart.SalePrice = 10; | ||
777 | |||
778 | if (m_Scene.Permissions.PropagatePermissions()) | ||
726 | { | 779 | { |
727 | part.EveryoneMask = item.EveryOnePermissions; | 780 | foreach (SceneObjectPart part in group.Parts) |
728 | part.NextOwnerMask = item.NextPermissions; | 781 | { |
729 | part.GroupMask = 0; // DO NOT propagate here | 782 | if ((item.Flags & (uint)InventoryItemFlags.ObjectHasMultipleItems) == 0) |
783 | { | ||
784 | part.EveryoneMask = item.EveryOnePermissions; | ||
785 | part.NextOwnerMask = item.NextPermissions; | ||
786 | } | ||
787 | part.GroupMask = 0; // DO NOT propagate here | ||
788 | } | ||
789 | |||
790 | group.ApplyNextOwnerPermissions(); | ||
730 | } | 791 | } |
731 | |||
732 | group.ApplyNextOwnerPermissions(); | ||
733 | } | 792 | } |
734 | } | ||
735 | if (group.UUID == UUID.Zero) | ||
736 | { | ||
737 | m_log.Debug("[InventoryAccessModule]: Inventory object has UUID.Zero! Position 8"); | ||
738 | } | ||
739 | 793 | ||
740 | foreach (SceneObjectPart part in group.Parts) | 794 | foreach (SceneObjectPart part in group.Parts) |
741 | { | ||
742 | if ((part.OwnerID != item.Owner) || (item.CurrentPermissions & 16) != 0) | ||
743 | { | 795 | { |
744 | part.LastOwnerID = part.OwnerID; | 796 | if ((part.OwnerID != item.Owner) || |
745 | part.OwnerID = item.Owner; | 797 | (item.CurrentPermissions & 16) != 0) |
746 | part.Inventory.ChangeInventoryOwner(item.Owner); | 798 | { |
747 | part.GroupMask = 0; // DO NOT propagate here | 799 | part.LastOwnerID = part.OwnerID; |
800 | part.OwnerID = item.Owner; | ||
801 | part.Inventory.ChangeInventoryOwner(item.Owner); | ||
802 | part.GroupMask = 0; // DO NOT propagate here | ||
803 | } | ||
804 | part.EveryoneMask = item.EveryOnePermissions; | ||
805 | part.NextOwnerMask = item.NextPermissions; | ||
748 | } | 806 | } |
749 | part.EveryoneMask = item.EveryOnePermissions; | 807 | |
750 | part.NextOwnerMask = item.NextPermissions; | 808 | rootPart.TrimPermissions(); |
751 | } | 809 | |
752 | if (group.UUID == UUID.Zero) | 810 | if (!attachment) |
753 | { | ||
754 | m_log.Debug("[InventoryAccessModule]: Inventory object has UUID.Zero! Position 9"); | ||
755 | } | ||
756 | rootPart.TrimPermissions(); | ||
757 | if (group.UUID == UUID.Zero) | ||
758 | { | ||
759 | m_log.Debug("[InventoryAccessModule]: Inventory object has UUID.Zero! Position 10"); | ||
760 | } | ||
761 | if (!attachment) | ||
762 | { | ||
763 | if (group.RootPart.Shape.PCode == (byte)PCode.Prim) | ||
764 | { | 811 | { |
765 | // Save attachment data | 812 | if (group.RootPart.Shape.PCode == (byte)PCode.Prim) |
766 | group.RootPart.AttachPoint = group.RootPart.Shape.State; | 813 | { |
767 | group.RootPart.AttachOffset = storedPosition; | 814 | // Save attachment data |
815 | group.RootPart.AttachPoint = group.RootPart.Shape.State; | ||
816 | group.RootPart.AttachOffset = storedPosition; | ||
768 | 817 | ||
769 | group.ClearPartAttachmentData(); | 818 | group.ClearPartAttachmentData(); |
770 | } | 819 | } |
771 | 820 | ||
772 | // Fire on_rez | 821 | // Fire on_rez |
773 | group.CreateScriptInstances(0, true, m_Scene.DefaultScriptEngine, 1); | 822 | group.CreateScriptInstances(0, true, m_Scene.DefaultScriptEngine, 1); |
774 | rootPart.ParentGroup.ResumeScripts(); | 823 | rootPart.ParentGroup.ResumeScripts(); |
775 | 824 | ||
776 | rootPart.ScheduleFullUpdate(); | 825 | rootPart.ScheduleFullUpdate(); |
826 | } | ||
777 | } | 827 | } |
778 | 828 | ||
779 | if (!m_Scene.Permissions.BypassPermissions()) | 829 | if (!m_Scene.Permissions.BypassPermissions()) |
@@ -791,12 +841,8 @@ namespace OpenSim.Region.CoreModules.Framework.InventoryAccess | |||
791 | } | 841 | } |
792 | } | 842 | } |
793 | } | 843 | } |
794 | if (group.UUID == UUID.Zero) | ||
795 | { | ||
796 | m_log.Debug("[InventoryAccessModule]: Inventory object has UUID.Zero! Position 11"); | ||
797 | } | ||
798 | return group; | ||
799 | } | 844 | } |
845 | return group; | ||
800 | } | 846 | } |
801 | 847 | ||
802 | return null; | 848 | return null; |