/* * Copyright (c) 2007, Second Life Reverse Engineering Team * All rights reserved. * * - Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are met: * * - Redistributions of source code must retain the above copyright notice, this * list of conditions and the following disclaimer. * - Neither the name of the Second Life Reverse Engineering Team nor the names * of its contributors may be used to endorse or promote products derived from * this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE * POSSIBILITY OF SUCH DAMAGE. */ using System; using System.Collections.Generic; using System.Xml; using System.Xml.Serialization; using libsecondlife.Packets; namespace libsecondlife { /// /// Base class for primitives and avatars /// [Serializable] public abstract partial class LLObject { #region Enumerations /// /// Primary parameters for primitives such as Physics Enabled or Phantom /// [Flags] public enum ObjectFlags : uint { /// None of the primary flags are enabled None = 0, /// Whether physics are enabled for this object Physics = 0x00000001, /// CreateSelected = 0x00000002, /// ObjectModify = 0x00000004, /// ObjectCopy = 0x00000008, /// ObjectAnyOwner = 0x00000010, /// ObjectYouOwner = 0x00000020, /// Scripted = 0x00000040, /// Whether this object contains an active touch script Touch = 0x00000080, /// ObjectMove = 0x00000100, /// Whether this object can receive payments Money = 0x00000200, /// Whether this object is phantom (no collisions) Phantom = 0x00000400, /// InventoryEmpty = 0x00000800, /// JointHinge = 0x00001000, /// JointP2P = 0x00002000, /// JointLP2P = 0x00004000, /// Deprecated JointWheel = 0x00008000, /// AllowInventoryDrop = 0x00010000, /// ObjectTransfer = 0x00020000, /// ObjectGroupOwned = 0x00040000, /// Deprecated ObjectYouOfficer = 0x00080000, /// CameraDecoupled = 0x00100000, /// AnimSource = 0x00200000, /// CameraSource = 0x00400000, /// CastShadows = 0x00800000, /// ObjectOwnerModify = 0x10000000, /// TemporaryOnRez = 0x20000000, /// Temporary = 0x40000000, /// ZlibCompressed = 0x80000000 } #endregion Enumerations #region Structs /// /// /// [Serializable] public struct ObjectData { /// [XmlAttribute("pathtwistbegin")] public int PathTwistBegin; /// [XmlAttribute("pathend")] public float PathEnd; /// [XmlAttribute("profilebegin")] public float ProfileBegin; /// [XmlAttribute("pathradiusoffset")] public float PathRadiusOffset; /// [XmlAttribute("pathskew")] public float PathSkew; /// [XmlAttribute("profilecurve")] public uint ProfileCurve; /// [XmlAttribute("pathscalex")] public float PathScaleX; /// [XmlAttribute("pathscaley")] public float PathScaleY; /// [XmlAttribute("material")] public uint Material; /// [XmlAttribute("pathshearx")] public float PathShearX; /// [XmlAttribute("pathsheary")] public float PathShearY; /// [XmlAttribute("pathtaperx")] public float PathTaperX; /// [XmlAttribute("pathtapery")] public float PathTaperY; /// [XmlAttribute("profileend")] public float ProfileEnd; /// [XmlAttribute("pathbegin")] public float PathBegin; /// [XmlAttribute("pathcurve")] public uint PathCurve; /// [XmlAttribute("pathtwist")] public int PathTwist; /// [XmlAttribute("profilehollow")] public uint ProfileHollow; /// [XmlAttribute("pathrevolutions")] public float PathRevolutions; /// [XmlAttribute("state")] public uint State; /// [XmlIgnore] public ObjectManager.PCode PCode; } /// /// /// public struct ObjectProperties { /// public LLUUID ObjectID; /// public LLUUID CreatorID; /// public LLUUID OwnerID; /// public LLUUID GroupID; /// public ulong CreationDate; /// public uint BaseMask; /// public uint OwnerMask; /// public uint GroupMask; /// public uint EveryoneMask; /// public uint NextOwnerMask; /// public int OwnershipCost; /// public byte SaleType; /// public int SalePrice; /// public byte AggregatePerms; /// public byte AggregatePermTextures; /// public byte AggregatePermTexturesOwner; /// public uint Category; /// public short InventorySerial; /// public LLUUID ItemID; /// public LLUUID FolderID; /// public LLUUID FromTaskID; /// public LLUUID LastOwnerID; /// public string Name; /// public string Description; /// public string TouchName; /// public string SitName; /// public LLUUID[] TextureIDs; } /// /// /// public struct ObjectPropertiesFamily { /// /// /// public enum RequestFlagsType { /// BugReportRequest = 1, /// ComplaintReportRequest = 2 } /// public RequestFlagsType RequestFlags; /// public LLUUID ObjectID; /// public LLUUID OwnerID; /// public LLUUID GroupID; /// public uint BaseMask; /// public uint OwnerMask; /// public uint GroupMask; /// public uint EveryoneMask; /// public uint NextOwnerMask; /// public int OwnershipCost; /// public byte SaleType; /// public int SalePrice; /// public uint Category; /// public LLUUID LastOwnerID; /// public string Name; /// public string Description; } #endregion Structs #region Public Members /// public LLUUID ID = LLUUID.Zero; /// public LLUUID GroupID = LLUUID.Zero; /// public uint LocalID; /// public uint ParentID; /// public ulong RegionHandle; /// public ObjectFlags Flags; /// Unknown public byte[] GenericData; /// public LLVector3 Position; /// public LLVector3 Scale; /// public LLQuaternion Rotation = LLQuaternion.Identity; /// public LLVector3 Velocity; /// public LLVector3 AngularVelocity; /// public LLVector3 Acceleration; /// public LLVector4 CollisionPlane; /// public TextureEntry Textures; /// public ObjectProperties Properties; /// public ObjectPropertiesFamily PropertiesFamily; /// public SerializableDictionary NameValues = new SerializableDictionary(); #endregion Public Members #region Public Properties /// public ObjectData Data { get { return data; } } #endregion Public Properties internal ObjectData data = new ObjectData(); public override bool Equals(object obj) { LLObject llobj = obj as LLObject; if (llobj == null) return false; return ID.Equals(llobj.ID); } public override int GetHashCode() { return ID.GetHashCode(); } #region Static Methods /// /// /// /// /// public static byte PathScaleByte(float pathScale) { // Y = 100 + 100X int scale = (int)Math.Round(100.0f * pathScale); return (byte)(100 + scale); } /// /// /// /// /// public static float PathScaleFloat(byte pathScale) { // Y = -1 + 0.01X return (float)Math.Round((double)pathScale * 0.01d - 1.0d, 6); } /// /// /// /// /// public static byte PathShearByte(float pathShear) { // Y = 256 + 100X int shear = (int)Math.Round(100.0f * pathShear); shear += 256; return (byte)(shear % 256); } /// /// /// /// /// public static float PathShearFloat(byte pathShear) { if (pathShear == 0) return 0.0f; if (pathShear > 150) { // Negative value return ((float)pathShear - 256.0f) / 100.0f; } else { // Positive value return (float)pathShear / 100.0f; } } /// /// /// /// /// public static byte ProfileBeginByte(float profileBegin) { // Y = ceil (200X) return (byte)Math.Round(200.0f * profileBegin); } /// /// /// /// /// public static float ProfileBeginFloat(byte profileBegin) { // Y = 0.005X return (float)Math.Round((double)profileBegin * 0.005d, 6); } /// /// /// /// /// public static byte ProfileEndByte(float profileEnd) { // Y = 200 - 200X int end = (int)Math.Round(200.0d * (double)profileEnd); return (byte)(200 - end); } /// /// /// /// /// public static float ProfileEndFloat(byte profileEnd) { // Y = 1 - 0.005X return (float)Math.Round(1.0d - ((double)profileEnd * 0.005d), 6); } /// /// /// /// /// public static byte PathBeginByte(float pathBegin) { // Y = 100X return (byte)Convert.ToInt16(100.0f * pathBegin); } /// /// /// /// /// public static float PathBeginFloat(byte pathBegin) { // Y = X / 100 return (float)pathBegin / 100.0f; } /// /// /// /// /// public static byte PathEndByte(float pathEnd) { // Y = 100 - 100X int end = (int)Math.Round(100.0f * pathEnd); return (byte)(100 - end); } /// /// /// /// /// public static float PathEndFloat(byte pathEnd) { // Y = 1 - X / 100 return 1.0f - (float)pathEnd / 100.0f; } /// /// /// /// /// public static sbyte PathRadiusOffsetByte(float pathRadiusOffset) { // Y = 256 + 100X return (sbyte)PathShearByte(pathRadiusOffset); } /// /// /// /// /// public static float PathRadiusOffsetFloat(sbyte pathRadiusOffset) { // Y = X / 100 return (float)pathRadiusOffset / 100.0f; } /// /// /// /// /// public static byte PathRevolutionsByte(float pathRevolutions) { // Y = 66.5X - 66 int revolutions = (int)Math.Round(66.5d * (double)pathRevolutions); return (byte)(revolutions - 66); } /// /// /// /// /// public static float PathRevolutionsFloat(byte pathRevolutions) { // Y = 1 + 0.015X return (float)Math.Round(1.0d + (double)pathRevolutions * 0.015d, 6); } /// /// /// /// /// public static sbyte PathSkewByte(float pathSkew) { return PathTaperByte(pathSkew); } /// /// /// /// /// public static float PathSkewFloat(sbyte pathSkew) { return PathTaperFloat(pathSkew); } /// /// /// /// /// public static sbyte PathTaperByte(float pathTaper) { // Y = 256 + 100X return (sbyte)PathShearByte(pathTaper); } /// /// /// /// /// public static float PathTaperFloat(sbyte pathTaper) { return (float)pathTaper / 100.0f; } #endregion Static Methods } }