void Objects_OnObjectUpdated(Simulator simulator, ObjectMovementUpdate update, ulong regionHandle, ushort timeDilation) { if (!update.Avatar) { Primitive prim; if (prims.TryGetValue(update.LocalID, out prim)) { lock (prim) { if (Program.Verbosity > 1) { Logger.Log("Updating state for " + prim.ID.ToString(), Helpers.LogLevel.Info); } prim.Acceleration = update.Acceleration; prim.AngularVelocity = update.AngularVelocity; prim.CollisionPlane = update.CollisionPlane; prim.Position = update.Position; prim.Rotation = update.Rotation; prim.PrimData.State = update.State; prim.Textures = update.Textures; prim.Velocity = update.Velocity; } UpdateTextureQueue(prim.Textures); } } }
public static void updateToPrim(Primitive prim, ObjectMovementUpdate update) { prim.Acceleration = update.Acceleration; prim.AngularVelocity = update.AngularVelocity; prim.CollisionPlane = update.CollisionPlane; prim.Position = update.Position; prim.Rotation = update.Rotation; prim.PrimData.State = update.State; if (update.Textures != null) { prim.Textures = update.Textures; } prim.Velocity = update.Velocity; }
public static ObjectMovementUpdate updateDiff(ObjectMovementUpdate fromPrim, ObjectMovementUpdate diff) { ObjectMovementUpdate update;// = new ObjectMovementUpdate(); update.LocalID = fromPrim.LocalID; update.Avatar = fromPrim.Avatar; update.Acceleration = fromPrim.Acceleration - diff.Acceleration; update.AngularVelocity = fromPrim.AngularVelocity - diff.AngularVelocity; update.CollisionPlane = fromPrim.CollisionPlane - diff.CollisionPlane; update.Position = fromPrim.Position - diff.Position; update.Rotation = fromPrim.Rotation - diff.Rotation; update.State = (byte)(fromPrim.State - diff.State); update.Textures = fromPrim.Textures != diff.Textures ? diff.Textures : null; update.Velocity = fromPrim.Velocity - diff.Velocity; return(update); }
public void Objects_OnPrimitiveUpdateRealDead(Simulator simulator, ObjectMovementUpdate update, ulong regionHandle, ushort timeDilation) { throw new InvalidOperationException("Objects_OnObjectProperties"); /// return; if (simulator.Handle != regionHandle) { Debug("Strange update" + simulator); //base.Objects_OnObjectUpdated(simulator, update, regionHandle, timeDilation); } // return; CheckConnected(simulator); //all things if (update.Avatar) Primitive av = GetPrimitive(update.LocalID, simulator); Objects_OnObjectUpdated1(simulator, av, update, regionHandle, timeDilation); }
public static ObjectMovementUpdate updatFromSimObject(SimObject from) { ObjectMovementUpdate update = new ObjectMovementUpdate(); if (from.Prim != null) { update.Acceleration = from.Prim.Acceleration; update.AngularVelocity = from.Prim.AngularVelocity; update.CollisionPlane = from.Prim.CollisionPlane; update.Position = from.Prim.Position; update.Rotation = from.Prim.Rotation; update.State = from.Prim.PrimData.State; if (from.Prim.Textures != null) { update.Textures = from.Prim.Textures; } update.Velocity = from.Prim.Velocity; update.LocalID = from.Prim.LocalID; } update.Avatar = (from is SimAvatar); return(update); }
public void OnTerseObjectUpdate(object sender, TerseObjectUpdateEventArgs e) { ObjectMovementUpdate omu = e.Update; Avatar avatar; m_GridClient.Network.CurrentSim.ObjectsAvatars.TryGetValue(e.Update.LocalID, out avatar); if (avatar != null && avatar.Name != "") { if (avatar.Name == CONDUCTOR) { m_ir.UpdateState(m_GridClient.Self.RelativePosition, avatar.Position); Debug.WriteLine("UUID = " + avatar.ID); if (Vector3.Distance(m_GridClient.Self.RelativePosition, avatar.Position) < 5) { Debug.WriteLine("collision happened between player and " + m_GridClient.Self.Name); } } // follow avatar FollowAvatar(avatar); } }
public override void UpdateObject(ObjectMovementUpdate objectUpdate, ObjectMovementUpdate objectUpdateDiff) { }
// Processes object update packets (Avatars and Objects entering drawing distance) private Packet ProcessObjectUpdate(Packet packet, IPEndPoint endpoint) { ObjectUpdatePacket update = (ObjectUpdatePacket)packet; for (int b = 0; b < update.ObjectData.Length; b++) { ObjectUpdatePacket.ObjectDataBlock block = update.ObjectData[b]; ObjectMovementUpdate objectupdate = new ObjectMovementUpdate(); NameValue[] nameValues; string firstname = ""; string lastname = ""; PCode pcode = (PCode)block.PCode; #region NameValue parsing string nameValue = Utils.BytesToString(block.NameValue); if (nameValue.Length > 0) { string[] lines = nameValue.Split('\n'); nameValues = new NameValue[lines.Length]; for (int i = 0; i < lines.Length; i++) { if (!String.IsNullOrEmpty(lines[i])) { NameValue nv = new NameValue(lines[i]); if (nv.Name == "FirstName") { firstname = nv.Value.ToString(); } if (nv.Name == "LastName") { lastname = nv.Value.ToString(); } nameValues[i] = nv; } } } else { nameValues = new NameValue[0]; } #endregion NameValue parsing #region Decode Object (primitive) parameters Primitive.ConstructionData data = new Primitive.ConstructionData(); data.State = block.State; data.Material = (Material)block.Material; data.PathCurve = (PathCurve)block.PathCurve; data.profileCurve = block.ProfileCurve; data.PathBegin = Primitive.UnpackBeginCut(block.PathBegin); data.PathEnd = Primitive.UnpackEndCut(block.PathEnd); data.PathScaleX = Primitive.UnpackPathScale(block.PathScaleX); data.PathScaleY = Primitive.UnpackPathScale(block.PathScaleY); data.PathShearX = Primitive.UnpackPathShear((sbyte)block.PathShearX); data.PathShearY = Primitive.UnpackPathShear((sbyte)block.PathShearY); data.PathTwist = Primitive.UnpackPathTwist(block.PathTwist); data.PathTwistBegin = Primitive.UnpackPathTwist(block.PathTwistBegin); data.PathRadiusOffset = Primitive.UnpackPathTwist(block.PathRadiusOffset); data.PathTaperX = Primitive.UnpackPathTaper(block.PathTaperX); data.PathTaperY = Primitive.UnpackPathTaper(block.PathTaperY); data.PathRevolutions = Primitive.UnpackPathRevolutions(block.PathRevolutions); data.PathSkew = Primitive.UnpackPathTwist(block.PathSkew); data.ProfileBegin = Primitive.UnpackBeginCut(block.ProfileBegin); data.ProfileEnd = Primitive.UnpackEndCut(block.ProfileEnd); data.ProfileHollow = Primitive.UnpackProfileHollow(block.ProfileHollow); data.PCode = pcode; #endregion #region Decode Additional packed parameters in ObjectData int pos = 0; switch (block.ObjectData.Length) { case 76: // Collision normal for avatar objectupdate.CollisionPlane = new Vector4(block.ObjectData, pos); pos += 16; goto case 60; case 60: // Position objectupdate.Position = new Vector3(block.ObjectData, pos); pos += 12; // Velocity objectupdate.Velocity = new Vector3(block.ObjectData, pos); pos += 12; // Acceleration objectupdate.Acceleration = new Vector3(block.ObjectData, pos); pos += 12; // Rotation (theta) objectupdate.Rotation = new Quaternion(block.ObjectData, pos, true); pos += 12; // Angular velocity (omega) objectupdate.AngularVelocity = new Vector3(block.ObjectData, pos); pos += 12; break; case 48: // Collision normal for avatar objectupdate.CollisionPlane = new Vector4(block.ObjectData, pos); pos += 16; goto case 32; case 32: // The data is an array of unsigned shorts // Position objectupdate.Position = new Vector3( Utils.UInt16ToFloat(block.ObjectData, pos, -0.5f * 256.0f, 1.5f * 256.0f), Utils.UInt16ToFloat(block.ObjectData, pos + 2, -0.5f * 256.0f, 1.5f * 256.0f), Utils.UInt16ToFloat(block.ObjectData, pos + 4, -256.0f, 3.0f * 256.0f)); pos += 6; // Velocity objectupdate.Velocity = new Vector3( Utils.UInt16ToFloat(block.ObjectData, pos, -256.0f, 256.0f), Utils.UInt16ToFloat(block.ObjectData, pos + 2, -256.0f, 256.0f), Utils.UInt16ToFloat(block.ObjectData, pos + 4, -256.0f, 256.0f)); pos += 6; // Acceleration objectupdate.Acceleration = new Vector3( Utils.UInt16ToFloat(block.ObjectData, pos, -256.0f, 256.0f), Utils.UInt16ToFloat(block.ObjectData, pos + 2, -256.0f, 256.0f), Utils.UInt16ToFloat(block.ObjectData, pos + 4, -256.0f, 256.0f)); pos += 6; // Rotation (theta) objectupdate.Rotation = new Quaternion( Utils.UInt16ToFloat(block.ObjectData, pos, -1.0f, 1.0f), Utils.UInt16ToFloat(block.ObjectData, pos + 2, -1.0f, 1.0f), Utils.UInt16ToFloat(block.ObjectData, pos + 4, -1.0f, 1.0f), Utils.UInt16ToFloat(block.ObjectData, pos + 6, -1.0f, 1.0f)); pos += 8; // Angular velocity (omega) objectupdate.AngularVelocity = new Vector3( Utils.UInt16ToFloat(block.ObjectData, pos, -256.0f, 256.0f), Utils.UInt16ToFloat(block.ObjectData, pos + 2, -256.0f, 256.0f), Utils.UInt16ToFloat(block.ObjectData, pos + 4, -256.0f, 256.0f)); pos += 6; break; case 16: // The data is an array of single bytes (8-bit numbers) // Position objectupdate.Position = new Vector3( Utils.ByteToFloat(block.ObjectData, pos, -256.0f, 256.0f), Utils.ByteToFloat(block.ObjectData, pos + 1, -256.0f, 256.0f), Utils.ByteToFloat(block.ObjectData, pos + 2, -256.0f, 256.0f)); pos += 3; // Velocity objectupdate.Velocity = new Vector3( Utils.ByteToFloat(block.ObjectData, pos, -256.0f, 256.0f), Utils.ByteToFloat(block.ObjectData, pos + 1, -256.0f, 256.0f), Utils.ByteToFloat(block.ObjectData, pos + 2, -256.0f, 256.0f)); pos += 3; // Accleration objectupdate.Acceleration = new Vector3( Utils.ByteToFloat(block.ObjectData, pos, -256.0f, 256.0f), Utils.ByteToFloat(block.ObjectData, pos + 1, -256.0f, 256.0f), Utils.ByteToFloat(block.ObjectData, pos + 2, -256.0f, 256.0f)); pos += 3; // Rotation objectupdate.Rotation = new Quaternion( Utils.ByteToFloat(block.ObjectData, pos, -1.0f, 1.0f), Utils.ByteToFloat(block.ObjectData, pos + 1, -1.0f, 1.0f), Utils.ByteToFloat(block.ObjectData, pos + 2, -1.0f, 1.0f), Utils.ByteToFloat(block.ObjectData, pos + 3, -1.0f, 1.0f)); pos += 4; // Angular Velocity objectupdate.AngularVelocity = new Vector3( Utils.ByteToFloat(block.ObjectData, pos, -256.0f, 256.0f), Utils.ByteToFloat(block.ObjectData, pos + 1, -256.0f, 256.0f), Utils.ByteToFloat(block.ObjectData, pos + 2, -256.0f, 256.0f)); pos += 3; break; default: SayToUser("ERROR: Got an ObjectUpdate block with ObjectUpdate field length of " + block.ObjectData.Length); continue; } #endregion // Determine the object type and create the appropriate class switch (pcode) { #region Prim and Foliage case PCode.Grass: case PCode.Tree: case PCode.NewTree: case PCode.Prim: break; #endregion Prim and Foliage #region Avatar case PCode.Avatar: if (block.FullID == this.frame.AgentID) { mylocalid = block.ID; StatusSetLocalID(mylocalid.ToString()); } #region Create an Avatar from the decoded data Avatar avatar = new Avatar(); if (Avatars.ContainsKey(block.ID)) { avatar = Avatars[block.ID]; } objectupdate.Avatar = true; // Textures objectupdate.Textures = new Primitive.TextureEntry(block.TextureEntry, 0, block.TextureEntry.Length); uint oldSeatID = avatar.ParentID; avatar.ID = block.FullID; avatar.LocalID = block.ID; avatar.CollisionPlane = objectupdate.CollisionPlane; avatar.Position = objectupdate.Position; avatar.Velocity = objectupdate.Velocity; avatar.Acceleration = objectupdate.Acceleration; avatar.Rotation = objectupdate.Rotation; avatar.AngularVelocity = objectupdate.AngularVelocity; avatar.NameValues = nameValues; avatar.PrimData = data; if (block.Data.Length > 0) { SayToUser("ERROR: Unexpected Data field for an avatar update, length " + block.Data.Length); } avatar.ParentID = block.ParentID; avatar.RegionHandle = update.RegionData.RegionHandle; // Textures avatar.Textures = objectupdate.Textures; // Save the avatar lock (Avatars) Avatars[block.ID] = avatar; // Fill up the translation dictionaries lock (AvatarIDtoUUID) AvatarIDtoUUID[block.ID] = block.FullID; lock (AvatarUUIDtoID) AvatarUUIDtoID[block.FullID] = block.ID; lock (AvatarUUIDToName) AvatarUUIDToName[block.FullID] = firstname + " " + lastname; lock (AvatarNameToUUID) AvatarNameToUUID[firstname + " " + lastname] = block.FullID; #endregion Create an Avatar from the decoded data break; #endregion Avatar case PCode.ParticleSystem: // ConsoleWriteLine("ERROR: Got a particle system update."); // // TODO: Create a callback for particle updates break; default: SayToUser("ERROR: Got an ObjectUpdate block with an unrecognized PCode " + pcode.ToString()); break; } } return(packet); }
private Object notifyUpdate(SimObject objectUpdated, ObjectMovementUpdate before, ObjectMovementUpdate after, DoWhat didUpdate) { ObjectMovementUpdate diff = updateDiff(before, after); bool wasChanged = false; bool wasPositionUpdateSent = false; if (before.Acceleration != after.Acceleration) { after.Acceleration = (Vector3) didUpdate(objectUpdated, "Acceleration", before.Acceleration, after.Acceleration, diff.Acceleration); wasChanged = true; } if (before.AngularVelocity != after.AngularVelocity) { after.AngularVelocity = (Vector3) didUpdate(objectUpdated, "AngularVelocity", before.AngularVelocity, after.AngularVelocity, diff.AngularVelocity); wasChanged = true; } if (false) { if (before.CollisionPlane != after.CollisionPlane) { after.CollisionPlane = (Vector4) didUpdate(objectUpdated, "CollisionPlane", before.CollisionPlane, after.CollisionPlane, diff.CollisionPlane); wasChanged = true; } } if (before.Position != after.Position) { after.Position = (Vector3)didUpdate(objectUpdated, "Position", before.Position, after.Position, diff.Position); wasChanged = true; wasPositionUpdateSent = true; } Quaternion diff1 = before.Rotation - after.Rotation; if (diff1.Length() > 0.1f) { after.Rotation = (Quaternion)didUpdate(objectUpdated, "Rotation", before.Rotation, after.Rotation, diff.Rotation); wasChanged = true; } if (false) { if (before.State != after.State) { didUpdate(objectUpdated, "State", before.State, after.State, diff.State); wasChanged = true; } } if (before.Textures != after.Textures) { //didUpdate(objectUpdated, "Textures", before.Textures, after.Textures, diff.Textures); //wasChanged = true; } if (before.Velocity != after.Velocity) { // didUpdate(objectUpdated, "Velocity", before.Velocity, after.Velocity, diff.Velocity); if (before.Velocity == Vector3.Zero) { SendNewUpdateEvent("on-object-start-velocity", objectUpdated, after.Velocity); if (!wasPositionUpdateSent) { SendNewUpdateEvent("on-object-position", objectUpdated, after.Position); } } else if (after.Velocity == Vector3.Zero) { if (!wasPositionUpdateSent) { SendNewUpdateEvent("on-object-position", objectUpdated, after.Position); } SendNewUpdateEvent("on-object-stop-velocity", objectUpdated, -before.Velocity); } else { //SendNewUpdateEvent("on-object-change-velosity", objectUpdated, after.Velocity); if (!wasPositionUpdateSent) { SendNewUpdateEvent("on-object-position", objectUpdated, after.Position); } } wasChanged = true; } if (!wasChanged) { return(null); } return(diff); }
public void Objects_OnObjectUpdated1(Simulator simulator, Primitive objectUpdated, ObjectMovementUpdate update, ulong regionHandle, ushort timeDilation) { if (!IsMaster(simulator)) { return; } if (objectUpdated != null) { //lock (objectUpdated) { // other OMV code already updated the Primitive // updateToPrim(prim, update); if (objectUpdated.Properties != null) { //CalcStats(objectUpdated); DeclareProperties(objectUpdated, objectUpdated.Properties, simulator); describePrimToAI(objectUpdated, simulator); } else { EnsureSelected(objectUpdated, simulator); } // Make a Last Object Update from the Primitive if we knew nothing about it if (MaintainObjectUpdates) { SimObject simObject = GetSimObject(objectUpdated, simulator); if (simObject != null) { lock (LastObjectUpdate) if (!LastObjectUpdate.ContainsKey(simObject)) { LastObjectUpdate[simObject] = updatFromSimObject(simObject); } if (m_TheSimAvatar != null) { //double dist = simObject.Distance(TheSimAvatar); //if (dist > 30 && !update.Avatar) return; } // Make a "diff" from previous ObjectMovementUpdate up; lock (LastObjectUpdate) up = LastObjectUpdate[simObject]; Object diffO = notifyUpdate(simObject, up, update, InformUpdate); if (diffO != null) { ObjectMovementUpdate diff = (ObjectMovementUpdate)diffO; //if (lastObjectUpdateDiff.ContainsKey(objectUpdated.ID)) //{ // notifyUpdate(objectUpdated, lastObjectUpdateDiff[objectUpdated.ID], diff, InformUpdateDiff); //} lock (LastObjectUpdateDiff) LastObjectUpdateDiff[objectUpdated.ID] = diff; } else { // someThingElseNeedsUpdate(objectUpdated); // needsOsdDiff = true; } ObjectMovementUpdate TheDiff = default(ObjectMovementUpdate); lock (LastObjectUpdateDiff) { if (LastObjectUpdateDiff.ContainsKey(objectUpdated.ID)) { TheDiff = LastObjectUpdateDiff[objectUpdated.ID]; } else { LastObjectUpdateDiff[objectUpdated.ID] = TheDiff; } } simObject.UpdateObject(update, TheDiff); lock (LastObjectUpdate) LastObjectUpdate[simObject] = update; } } } } else { //WriteLine("missing Objects_OnObjectUpdated"); } }
private void Objects_OnPrimitiveUpdateReal(Simulator simulator, Primitive av, ObjectMovementUpdate update, ulong RegionHandle, ushort TimeDilation) { if (!IsMaster(simulator)) { return; } if (av == null) { return; } if (av.ID == UUID.Zero) { return; // too early } SimObject AV = null; Object Obj; //lock (uuidTypeObject) if (UUIDTypeObjectTryGetValue(av.ID, out Obj)) { AV = Obj as SimObject; } else { if (av.ID == client.Self.AgentID) { AV = GetSimObject(av, simulator); } } if (AV != null) { Primitive prev = AV.Prim; if (prev == null) { AV.SetFirstPrim(av); } if (av.ParentID == 0 && !SimRegion.OutOfRegion(av.Position)) { AV.ResetPrim(av, client, simulator); } if (prev != null) { // parent changed? if (prev.ParentID != av.ParentID) { AV.Parent = null; } } if (av.ParentID == 0 && !SimRegion.OutOfRegion(update.Position)) { if (update.Avatar) { SimRegion.GetRegion(simulator).UpdateTraveled(av.ID, av.Position, av.Rotation); //return; } } if (!MaintainObjectUpdates) { return; } EventQueue.Enqueue(() => Objects_OnObjectUpdated1(simulator, av, updatFromSimObject(AV), RegionHandle, TimeDilation)); } }
private void PrimtiveBlockUpdate(Simulator simulator, ObjectMovementUpdate objectupdate0, Primitive prim, ObjectUpdatePacket.ObjectDataBlock block, Primitive.ConstructionData data) { bool isNewPrim = prim.Scale == Vector3.Zero && prim.Position == Vector3.Zero && prim.NameValues == null; if (prim.ID == UUID.Zero) { if (!simulator.Client.Settings.OBJECT_TRACKING) { throw new ArgumentException("Need to enable object tracking!!"); } SimObject O = GetSimObjectFromUUID(block.FullID); if (O == null) { Debug("PrimData ZERO for " + prim); if (block.ID > 0) { uint localID = block.ID; prim.LocalID = localID; prim.ID = block.FullID; // var p = simulator.Client.Objects.GetPrimitive(simulator, block.ID, block.FullID, false); // simulator.GetPrimitive( } } else { Debug("SimData ZERO for " + prim); uint localID = block.ID; prim.LocalID = localID; prim.ID = block.FullID; O.IsDebugging = true; } } // else { if (prim.RegionHandle == simulator.Handle && prim.ID != UUID.Zero) { if (!prim.PrimData.Equals(data) /* || prim.Scale != block.Scale || prim.Position != objectupdate.Position || prim.Rotation != objectupdate.Rotation || prim.ParentID != block.ParentID*/ ) { SimObject O = GetSimObjectFromUUID(prim.ID); if (O != null) { if (!isNewPrim) { Debug("PrimData changed for " + prim); O.PathFinding.RemoveCollisions(); } // the old OnNewPrim code will force the reindexing } else { //Debug("PrimData new for " + prim); O = GetSimObject(prim, simulator); return; } } if (!isNewPrim) { DeclareProperties(prim, prim.Properties, simulator); SendNewRegionEvent(SimEventType.DATA_UPDATE, "on-data-updated", prim); } //Objects_OnPrimitiveUpdate(simulator, prim, objectupdate0, simulator.Handle, 0); } else { //if (prim.RegionHandle == 0) // prim.RegionHandle = simulator.Handle; if (prim.ID != UUID.Zero) { SimObject O = GetSimObjectFromUUID(prim.ID); if (O != null && prim.Properties != null && prim.RegionHandle == simulator.Handle) { Objects_OnPrimitiveUpdateReal(simulator, prim, objectupdate0, simulator.Handle, 0); //O = GetSimObject(prim, simulator); } } } } }