From cdbeb8b83b671df1ffb6bf7890c64a27e4a85730 Mon Sep 17 00:00:00 2001 From: John Hurliman Date: Wed, 28 Oct 2009 03:21:53 -0700 Subject: Track timestamps when terse updates were last sent for a prim or avatar to avoid floating away forever until a key is pressed (deviates from SL behavior in a hopefully good way) --- OpenSim/Region/Framework/Scenes/ScenePresence.cs | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) (limited to 'OpenSim/Region/Framework/Scenes/ScenePresence.cs') diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index 87fac0c..92f00c4 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -96,6 +96,7 @@ namespace OpenSim.Region.Framework.Scenes private Vector3 m_lastPosition; private Quaternion m_lastRotation; private Vector3 m_lastVelocity; + private int m_lastTerseSent; private bool m_updateflag; private byte m_movementflag; @@ -2363,6 +2364,7 @@ namespace OpenSim.Region.Framework.Scenes { const float VELOCITY_TOLERANCE = 0.01f; const float POSITION_TOLERANCE = 10.0f; + const int TIME_MS_TOLERANCE = 3000; SendPrimUpdates(); @@ -2377,7 +2379,8 @@ namespace OpenSim.Region.Framework.Scenes // Throw away duplicate or insignificant updates if (m_bodyRot != m_lastRotation || (m_velocity - m_lastVelocity).Length() > VELOCITY_TOLERANCE || - (m_pos - m_lastPosition).Length() > POSITION_TOLERANCE) + (m_pos - m_lastPosition).Length() > POSITION_TOLERANCE || + Environment.TickCount - m_lastTerseSent > TIME_MS_TOLERANCE) { SendTerseUpdateToAllClients(); @@ -2385,6 +2388,7 @@ namespace OpenSim.Region.Framework.Scenes m_lastPosition = m_pos; m_lastRotation = m_bodyRot; m_lastVelocity = m_velocity; + m_lastTerseSent = Environment.TickCount; } // followed suggestion from mic bowman. reversed the two lines below. -- cgit v1.1 From a65c8cdc38f40a54ad4a14ed2e6168fb432c6e51 Mon Sep 17 00:00:00 2001 From: John Hurliman Date: Wed, 28 Oct 2009 12:45:40 -0700 Subject: * Reduce the velocity tolerance on sending terse updates to avoid slowly drifting prims/avatars * Added contacts_per_collision to the ODE config section. This allows you to reduce the maximum number of contact points ODE will generate per collision and reduce the size of the array that stores contact structures --- OpenSim/Region/Framework/Scenes/ScenePresence.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'OpenSim/Region/Framework/Scenes/ScenePresence.cs') diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index 92f00c4..9ba19d3 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -2362,7 +2362,7 @@ namespace OpenSim.Region.Framework.Scenes public override void Update() { - const float VELOCITY_TOLERANCE = 0.01f; + const float VELOCITY_TOLERANCE = 0.0001f; const float POSITION_TOLERANCE = 10.0f; const int TIME_MS_TOLERANCE = 3000; -- cgit v1.1 From b81c829576dd916c0a7bf141919f5e13f025d818 Mon Sep 17 00:00:00 2001 From: John Hurliman Date: Wed, 28 Oct 2009 14:13:17 -0700 Subject: * Standalone logins will now go through the sequence of "requested region, default region, any region" before giving up * Hip offset should have been added not subtracted (it's a negative offset). This puts avatar feet closer to the ground * Improved duplicate checking for terse updates. This should reduce bandwidth and walking through walls --- OpenSim/Region/Framework/Scenes/ScenePresence.cs | 21 ++++++++++++--------- 1 file changed, 12 insertions(+), 9 deletions(-) (limited to 'OpenSim/Region/Framework/Scenes/ScenePresence.cs') diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index 9ba19d3..63c979f 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -2362,8 +2362,9 @@ namespace OpenSim.Region.Framework.Scenes public override void Update() { - const float VELOCITY_TOLERANCE = 0.0001f; - const float POSITION_TOLERANCE = 10.0f; + const float ROTATION_TOLERANCE = 0.01f; + const float VELOCITY_TOLERANCE = 0.001f; + const float POSITION_TOLERANCE = 0.05f; const int TIME_MS_TOLERANCE = 3000; SendPrimUpdates(); @@ -2377,9 +2378,9 @@ namespace OpenSim.Region.Framework.Scenes if (m_isChildAgent == false) { // Throw away duplicate or insignificant updates - if (m_bodyRot != m_lastRotation || - (m_velocity - m_lastVelocity).Length() > VELOCITY_TOLERANCE || - (m_pos - m_lastPosition).Length() > POSITION_TOLERANCE || + if (!m_bodyRot.ApproxEquals(m_lastRotation, ROTATION_TOLERANCE) || + !m_velocity.ApproxEquals(m_lastVelocity, VELOCITY_TOLERANCE) || + !m_pos.ApproxEquals(m_lastPosition, POSITION_TOLERANCE) || Environment.TickCount - m_lastTerseSent > TIME_MS_TOLERANCE) { SendTerseUpdateToAllClients(); @@ -2415,7 +2416,9 @@ namespace OpenSim.Region.Framework.Scenes m_perfMonMS = Environment.TickCount; Vector3 pos = m_pos; - pos.Z -= m_appearance.HipOffset; + pos.Z += m_appearance.HipOffset; + + //m_log.DebugFormat("[SCENEPRESENCE]: TerseUpdate: Pos={0} Rot={1} Vel={2}", m_pos, m_bodyRot, m_velocity); remoteClient.SendAvatarTerseUpdate(new SendAvatarTerseData(m_regionHandle, (ushort)(m_scene.TimeDilation * ushort.MaxValue), LocalId, pos, m_velocity, Vector3.Zero, m_bodyRot, Vector4.UnitW, m_uuid, null, GetUpdatePriority(remoteClient))); @@ -2514,7 +2517,7 @@ namespace OpenSim.Region.Framework.Scenes return; Vector3 pos = m_pos; - pos.Z -= m_appearance.HipOffset; + pos.Z += m_appearance.HipOffset; remoteAvatar.m_controllingClient.SendAvatarData(new SendAvatarData(m_regionInfo.RegionHandle, m_firstname, m_lastname, m_grouptitle, m_uuid, LocalId, pos, m_appearance.Texture.GetBytes(), @@ -2585,7 +2588,7 @@ namespace OpenSim.Region.Framework.Scenes // m_scene.GetAvatarAppearance(m_controllingClient, out m_appearance); Vector3 pos = m_pos; - pos.Z -= m_appearance.HipOffset; + pos.Z += m_appearance.HipOffset; m_controllingClient.SendAvatarData(new SendAvatarData(m_regionInfo.RegionHandle, m_firstname, m_lastname, m_grouptitle, m_uuid, LocalId, pos, m_appearance.Texture.GetBytes(), m_parentID, m_bodyRot)); @@ -2694,7 +2697,7 @@ namespace OpenSim.Region.Framework.Scenes } Vector3 pos = m_pos; - pos.Z -= m_appearance.HipOffset; + pos.Z += m_appearance.HipOffset; m_controllingClient.SendAvatarData(new SendAvatarData(m_regionInfo.RegionHandle, m_firstname, m_lastname, m_grouptitle, m_uuid, LocalId, pos, m_appearance.Texture.GetBytes(), m_parentID, m_bodyRot)); -- cgit v1.1 From 59eb378d16fd8a9e887560a2744cc798fef08263 Mon Sep 17 00:00:00 2001 From: John Hurliman Date: Wed, 28 Oct 2009 23:10:16 -0700 Subject: Small performance tweaks to code called by the heartbeat loop --- OpenSim/Region/Framework/Scenes/ScenePresence.cs | 79 +++++------------------- 1 file changed, 17 insertions(+), 62 deletions(-) (limited to 'OpenSim/Region/Framework/Scenes/ScenePresence.cs') diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index 63c979f..1ea4585 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -76,8 +76,7 @@ namespace OpenSim.Region.Framework.Scenes private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); private static readonly byte[] BAKE_INDICES = new byte[] { 8, 9, 10, 11, 19, 20 }; - - public static byte[] DefaultTexture; + public static readonly byte[] DEFAULT_TEXTURE = AvatarAppearance.GetDefaultTexture().GetBytes(); public UUID currentParcelUUID = UUID.Zero; @@ -100,9 +99,9 @@ namespace OpenSim.Region.Framework.Scenes private bool m_updateflag; private byte m_movementflag; - private readonly List m_forcesList = new List(); + private Vector3? m_forceToApply; private uint m_requestedSitTargetID; - private UUID m_requestedSitTargetUUID = UUID.Zero; + private UUID m_requestedSitTargetUUID; private SendCourseLocationsMethod m_sendCourseLocationsMethod; private bool m_startAnimationSet; @@ -456,12 +455,9 @@ namespace OpenSim.Region.Framework.Scenes { get { - if (m_physicsActor != null) - { - m_velocity.X = m_physicsActor.Velocity.X; - m_velocity.Y = m_physicsActor.Velocity.Y; - m_velocity.Z = m_physicsActor.Velocity.Z; - } + PhysicsActor actor = m_physicsActor; + if (actor != null) + m_velocity = m_physicsActor.Velocity; return m_velocity; } @@ -2278,7 +2274,7 @@ namespace OpenSim.Region.Framework.Scenes { if (m_isChildAgent) { - m_log.Debug("DEBUG: AddNewMovement: child agent, Making root agent!"); + m_log.Debug("[SCENEPRESENCE]: AddNewMovement() called on child agent, making root agent!"); // we have to reset the user's child agent connections. // Likely, here they've lost the eventqueue for other regions so border @@ -2287,7 +2283,7 @@ namespace OpenSim.Region.Framework.Scenes List regions = new List(KnownChildRegionHandles); regions.Remove(m_scene.RegionInfo.RegionHandle); - MakeRootAgent(new Vector3(127, 127, 127), true); + MakeRootAgent(new Vector3(127f, 127f, 127f), true); // Async command if (m_scene.SceneGridService != null) @@ -2299,28 +2295,24 @@ namespace OpenSim.Region.Framework.Scenes System.Threading.Thread.Sleep(500); } - if (m_scene.SceneGridService != null) { m_scene.SceneGridService.EnableNeighbourChildAgents(this, new List()); } - - return; } m_perfMonMS = Environment.TickCount; m_rotation = rotation; - NewForce newVelocity = new NewForce(); Vector3 direc = vec * rotation; direc.Normalize(); direc *= 0.03f * 128f * m_speedModifier; if (m_physicsActor.Flying) { - direc *= 4; + direc *= 4.0f; //bool controlland = (((m_AgentControlFlags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_UP_NEG) != 0) || ((m_AgentControlFlags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_UP_NEG) != 0)); //bool colliding = (m_physicsActor.IsColliding==true); //if (controlland) @@ -2348,10 +2340,8 @@ namespace OpenSim.Region.Framework.Scenes } } - newVelocity.X = direc.X; - newVelocity.Y = direc.Y; - newVelocity.Z = direc.Z; - m_forcesList.Add(newVelocity); + // TODO: Add the force instead of only setting it to support multiple forces per frame? + m_forceToApply = direc; m_scene.StatsReporter.AddAgentTime(Environment.TickCount - m_perfMonMS); } @@ -3298,47 +3288,18 @@ namespace OpenSim.Region.Framework.Scenes /// public override void UpdateMovement() { - lock (m_forcesList) + if (m_forceToApply.HasValue) { - if (m_forcesList.Count > 0) - { - //we are only interested in the last velocity added to the list [Although they are called forces, they are actually velocities] - NewForce force = m_forcesList[m_forcesList.Count - 1]; + Vector3 force = m_forceToApply.Value; - m_updateflag = true; - try - { - movementvector.X = force.X; - movementvector.Y = force.Y; - movementvector.Z = force.Z; - Velocity = movementvector; - } - catch (NullReferenceException) - { - // Under extreme load, this returns a NullReference Exception that we can ignore. - // Ignoring this causes no movement to be sent to the physics engine... - // which when the scene is moving at 1 frame every 10 seconds, it doesn't really matter! - } + m_updateflag = true; + movementvector = force; + Velocity = force; - m_forcesList.Clear(); - } + m_forceToApply = null; } } - static ScenePresence() - { - Primitive.TextureEntry textu = AvatarAppearance.GetDefaultTexture(); - DefaultTexture = textu.GetBytes(); - - } - - public class NewForce - { - public float X; - public float Y; - public float Z; - } - public override void SetText(string text, Vector3 color, double alpha) { throw new Exception("Can't set Text on avatar."); @@ -3349,7 +3310,6 @@ namespace OpenSim.Region.Framework.Scenes /// public void AddToPhysicalScene(bool isFlying) { - PhysicsScene scene = m_scene.PhysicsScene; Vector3 pVec = AbsolutePosition; @@ -3478,11 +3438,6 @@ namespace OpenSim.Region.Framework.Scenes public ScenePresence() { - if (DefaultTexture == null) - { - Primitive.TextureEntry textu = AvatarAppearance.GetDefaultTexture(); - DefaultTexture = textu.GetBytes(); - } m_sendCourseLocationsMethod = SendCoarseLocationsDefault; CreateSceneViewer(); } -- cgit v1.1 From 713287707595061d7ce343db73edf3462d2d29fc Mon Sep 17 00:00:00 2001 From: John Hurliman Date: Thu, 29 Oct 2009 01:46:58 -0700 Subject: * Log progress messages when loading OAR files with a lot of assets * Change the PhysicsCollision callback for objects to send full contact point information. This will be used to calculate the collision plane for avatars * Send the physics engine velocity in terse updates, not the current force being applied to the avatar. This should fix several issues including crouching through the floor and walking through walls --- OpenSim/Region/Framework/Scenes/ScenePresence.cs | 20 ++++++++++++-------- 1 file changed, 12 insertions(+), 8 deletions(-) (limited to 'OpenSim/Region/Framework/Scenes/ScenePresence.cs') diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index 1ea4585..91044be 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -2367,9 +2367,11 @@ namespace OpenSim.Region.Framework.Scenes if (m_isChildAgent == false) { + Vector3 velocity = m_physicsActor.Velocity; + // Throw away duplicate or insignificant updates if (!m_bodyRot.ApproxEquals(m_lastRotation, ROTATION_TOLERANCE) || - !m_velocity.ApproxEquals(m_lastVelocity, VELOCITY_TOLERANCE) || + !velocity.ApproxEquals(m_lastVelocity, VELOCITY_TOLERANCE) || !m_pos.ApproxEquals(m_lastPosition, POSITION_TOLERANCE) || Environment.TickCount - m_lastTerseSent > TIME_MS_TOLERANCE) { @@ -2378,7 +2380,7 @@ namespace OpenSim.Region.Framework.Scenes // Update the "last" values m_lastPosition = m_pos; m_lastRotation = m_bodyRot; - m_lastVelocity = m_velocity; + m_lastVelocity = velocity; m_lastTerseSent = Environment.TickCount; } @@ -2411,7 +2413,7 @@ namespace OpenSim.Region.Framework.Scenes //m_log.DebugFormat("[SCENEPRESENCE]: TerseUpdate: Pos={0} Rot={1} Vel={2}", m_pos, m_bodyRot, m_velocity); remoteClient.SendAvatarTerseUpdate(new SendAvatarTerseData(m_regionHandle, (ushort)(m_scene.TimeDilation * ushort.MaxValue), LocalId, - pos, m_velocity, Vector3.Zero, m_bodyRot, Vector4.UnitW, m_uuid, null, GetUpdatePriority(remoteClient))); + pos, m_physicsActor.Velocity, Vector3.Zero, m_bodyRot, Vector4.UnitW, m_uuid, null, GetUpdatePriority(remoteClient))); m_scene.StatsReporter.AddAgentTime(Environment.TickCount - m_perfMonMS); m_scene.StatsReporter.AddAgentUpdates(1); @@ -3355,15 +3357,17 @@ namespace OpenSim.Region.Framework.Scenes // as of this comment the interval is set in AddToPhysicalScene UpdateMovementAnimations(); + CollisionEventUpdate collisionData = (CollisionEventUpdate)e; + Dictionary coldata = collisionData.m_objCollisionList; + if (m_invulnerable) return; - CollisionEventUpdate collisionData = (CollisionEventUpdate)e; - Dictionary coldata = collisionData.m_objCollisionList; + float starthealth = Health; uint killerObj = 0; foreach (uint localid in coldata.Keys) { - if (coldata[localid] <= 0.10f || m_invulnerable) + if (coldata[localid].PenetrationDepth <= 0.10f || m_invulnerable) continue; //if (localid == 0) //continue; @@ -3373,9 +3377,9 @@ namespace OpenSim.Region.Framework.Scenes if (part != null && part.ParentGroup.Damage != -1.0f) Health -= part.ParentGroup.Damage; else - Health -= coldata[localid] * 5; + Health -= coldata[localid].PenetrationDepth * 5.0f; - if (Health <= 0) + if (Health <= 0.0f) { if (localid != 0) killerObj = localid; -- cgit v1.1 From fd2c99f184fa192d316222f90ef76ec8b9726ada Mon Sep 17 00:00:00 2001 From: John Hurliman Date: Thu, 29 Oct 2009 02:10:48 -0700 Subject: Fixing NullReferenceException regression in the previous commit --- OpenSim/Region/Framework/Scenes/ScenePresence.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'OpenSim/Region/Framework/Scenes/ScenePresence.cs') diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index 91044be..7420134 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -2367,7 +2367,7 @@ namespace OpenSim.Region.Framework.Scenes if (m_isChildAgent == false) { - Vector3 velocity = m_physicsActor.Velocity; + Vector3 velocity = (m_physicsActor != null) ? m_physicsActor.Velocity : Vector3.Zero; // Throw away duplicate or insignificant updates if (!m_bodyRot.ApproxEquals(m_lastRotation, ROTATION_TOLERANCE) || -- cgit v1.1 From 3f2d6fe4707b6fbb40e775e63c4cd7a7137a9814 Mon Sep 17 00:00:00 2001 From: John Hurliman Date: Thu, 29 Oct 2009 04:13:51 -0700 Subject: Ported the Simian avatar animation system to OpenSim. Landing is currently not working --- OpenSim/Region/Framework/Scenes/ScenePresence.cs | 239 +++++++++++++++++++---- 1 file changed, 203 insertions(+), 36 deletions(-) (limited to 'OpenSim/Region/Framework/Scenes/ScenePresence.cs') diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index 7420134..c4f4021 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -130,12 +130,14 @@ namespace OpenSim.Region.Framework.Scenes private bool m_setAlwaysRun; private string m_movementAnimation = "DEFAULT"; - private long m_animPersistUntil = 0; - private bool m_allowFalling = false; - private bool m_useFlySlow = false; - private bool m_usePreJump = false; - private bool m_forceFly = false; - private bool m_flyDisabled = false; + private long m_animPersistUntil; + private int m_animTickFall; + private int m_animTickJump; + private bool m_allowFalling; + private bool m_useFlySlow; + private bool m_usePreJump; + private bool m_forceFly; + private bool m_flyDisabled; private float m_speedModifier = 1.0f; @@ -143,7 +145,7 @@ namespace OpenSim.Region.Framework.Scenes public bool IsRestrictedToRegion; - public string JID = string.Empty; + public string JID = String.Empty; // Agent moves with a PID controller causing a force to be exerted. private bool m_newCoarseLocations = true; @@ -158,43 +160,43 @@ namespace OpenSim.Region.Framework.Scenes private readonly Vector3[] Dir_Vectors = new Vector3[6]; // Position of agent's camera in world (region cordinates) - protected Vector3 m_CameraCenter = Vector3.Zero; - protected Vector3 m_lastCameraCenter = Vector3.Zero; + protected Vector3 m_CameraCenter; + protected Vector3 m_lastCameraCenter; protected Timer m_reprioritization_timer; - protected bool m_reprioritizing = false; - protected bool m_reprioritization_called = false; + protected bool m_reprioritizing; + protected bool m_reprioritization_called; // Use these three vectors to figure out what the agent is looking at // Convert it to a Matrix and/or Quaternion - protected Vector3 m_CameraAtAxis = Vector3.Zero; - protected Vector3 m_CameraLeftAxis = Vector3.Zero; - protected Vector3 m_CameraUpAxis = Vector3.Zero; + protected Vector3 m_CameraAtAxis; + protected Vector3 m_CameraLeftAxis; + protected Vector3 m_CameraUpAxis; private uint m_AgentControlFlags; private Quaternion m_headrotation = Quaternion.Identity; private byte m_state; //Reuse the Vector3 instead of creating a new one on the UpdateMovement method - private Vector3 movementvector = Vector3.Zero; + private Vector3 movementvector; private bool m_autopilotMoving; - private Vector3 m_autoPilotTarget = Vector3.Zero; + private Vector3 m_autoPilotTarget; private bool m_sitAtAutoTarget; private string m_nextSitAnimation = String.Empty; //PauPaw:Proper PID Controler for autopilot************ private bool m_moveToPositionInProgress; - private Vector3 m_moveToPositionTarget = Vector3.Zero; + private Vector3 m_moveToPositionTarget; - private bool m_followCamAuto = false; + private bool m_followCamAuto; - private int m_movementUpdateCount = 0; + private int m_movementUpdateCount; private const int NumMovementsBetweenRayCast = 5; - private bool CameraConstraintActive = false; - //private int m_moveToPositionStateStatus = 0; + private bool CameraConstraintActive; + //private int m_moveToPositionStateStatus; //***************************************************** // Agent's Draw distance. @@ -444,7 +446,7 @@ namespace OpenSim.Region.Framework.Scenes } m_pos = value; - m_parentPosition = new Vector3(0, 0, 0); + m_parentPosition = Vector3.Zero; } } @@ -457,22 +459,21 @@ namespace OpenSim.Region.Framework.Scenes { PhysicsActor actor = m_physicsActor; if (actor != null) - m_velocity = m_physicsActor.Velocity; + m_velocity = actor.Velocity; return m_velocity; } set { //m_log.DebugFormat("In {0} setting velocity of {1} to {2}", m_scene.RegionInfo.RegionName, Name, value); - - if (m_physicsActor != null) + + PhysicsActor actor = m_physicsActor; + if (actor != null) { try { lock (m_scene.SyncRoot) - { - m_physicsActor.Velocity = value; - } + actor.Velocity = value; } catch (Exception e) { @@ -934,7 +935,7 @@ namespace OpenSim.Region.Framework.Scenes isFlying = m_physicsActor.Flying; RemoveFromPhysicalScene(); - Velocity = new Vector3(0, 0, 0); + Velocity = Vector3.Zero; AbsolutePosition = pos; AddToPhysicalScene(isFlying); if (m_appearance != null) @@ -982,12 +983,13 @@ namespace OpenSim.Region.Framework.Scenes if (m_avHeight != 127.0f) { - AbsolutePosition = AbsolutePosition + new Vector3(0, 0, (m_avHeight / 6f)); + AbsolutePosition = AbsolutePosition + new Vector3(0f, 0f, (m_avHeight / 6f)); } else { - AbsolutePosition = AbsolutePosition + new Vector3(0, 0, (1.56f / 6f)); + AbsolutePosition = AbsolutePosition + new Vector3(0f, 0f, (1.56f / 6f)); } + TrySetMovementAnimation("LAND"); SendFullUpdateToAllClients(); } @@ -1534,7 +1536,7 @@ namespace OpenSim.Region.Framework.Scenes if (part != null) { AbsolutePosition = part.AbsolutePosition; - Velocity = new Vector3(0, 0, 0); + Velocity = Vector3.Zero; SendFullUpdateToAllClients(); //HandleAgentSit(ControllingClient, m_requestedSitTargetUUID); @@ -1851,7 +1853,7 @@ namespace OpenSim.Region.Framework.Scenes } m_parentID = m_requestedSitTargetID; - Velocity = new Vector3(0, 0, 0); + Velocity = Vector3.Zero; RemoveFromPhysicalScene(); TrySetMovementAnimation(sitAnimation); @@ -2008,7 +2010,7 @@ namespace OpenSim.Region.Framework.Scenes protected void TrySetMovementAnimation(string anim) { //m_log.DebugFormat("Updating movement animation to {0}", anim); - + if (!m_isChildAgent) { if (m_animations.TrySetDefaultAnimation(anim, m_controllingClient.NextAnimationSequenceNumber, UUID.Zero)) @@ -2239,12 +2241,176 @@ namespace OpenSim.Region.Framework.Scenes } } + public string GetMovementAnimation2() + { + const float FALL_DELAY = 0.33f; + const float PREJUMP_DELAY = 0.25f; + + m_allowFalling = true; + + AgentManager.ControlFlags controlFlags = (AgentManager.ControlFlags)m_AgentControlFlags; + PhysicsActor actor = m_physicsActor; + + // Create forward and left vectors from the current avatar rotation + Matrix4 rotMatrix = Matrix4.CreateFromQuaternion(m_bodyRot); + Vector3 fwd = Vector3.Transform(Vector3.UnitX, rotMatrix); + Vector3 left = Vector3.Transform(Vector3.UnitY, rotMatrix); + + // Check control flags + bool heldForward = (controlFlags & AgentManager.ControlFlags.AGENT_CONTROL_AT_POS) == AgentManager.ControlFlags.AGENT_CONTROL_AT_POS; + bool heldBack = (controlFlags & AgentManager.ControlFlags.AGENT_CONTROL_AT_NEG) == AgentManager.ControlFlags.AGENT_CONTROL_AT_NEG; + bool heldLeft = (controlFlags & AgentManager.ControlFlags.AGENT_CONTROL_LEFT_POS) == AgentManager.ControlFlags.AGENT_CONTROL_LEFT_POS; + bool heldRight = (controlFlags & AgentManager.ControlFlags.AGENT_CONTROL_LEFT_NEG) == AgentManager.ControlFlags.AGENT_CONTROL_LEFT_NEG; + //bool heldTurnLeft = (controlFlags & AgentManager.ControlFlags.AGENT_CONTROL_TURN_LEFT) == AgentManager.ControlFlags.AGENT_CONTROL_TURN_LEFT; + //bool heldTurnRight = (controlFlags & AgentManager.ControlFlags.AGENT_CONTROL_TURN_RIGHT) == AgentManager.ControlFlags.AGENT_CONTROL_TURN_RIGHT; + bool heldUp = (controlFlags & AgentManager.ControlFlags.AGENT_CONTROL_UP_POS) == AgentManager.ControlFlags.AGENT_CONTROL_UP_POS; + bool heldDown = (controlFlags & AgentManager.ControlFlags.AGENT_CONTROL_UP_NEG) == AgentManager.ControlFlags.AGENT_CONTROL_UP_NEG; + //bool flying = (controlFlags & AgentManager.ControlFlags.AGENT_CONTROL_FLY) == AgentManager.ControlFlags.AGENT_CONTROL_FLY; + //bool mouselook = (controlFlags & AgentManager.ControlFlags.AGENT_CONTROL_MOUSELOOK) == AgentManager.ControlFlags.AGENT_CONTROL_MOUSELOOK; + + // Direction in which the avatar is trying to move + Vector3 move = Vector3.Zero; + if (heldForward) { move.X += fwd.X; move.Y += fwd.Y; } + if (heldBack) { move.X -= fwd.X; move.Y -= fwd.Y; } + if (heldLeft) { move.X += left.X; move.Y += left.Y; } + if (heldRight) { move.X -= left.X; move.Y -= left.Y; } + if (heldUp) { move.Z += 1; } + if (heldDown) { move.Z -= 1; } + + // Is the avatar trying to move? + bool moving = (move != Vector3.Zero); + bool jumping = m_animTickJump != 0; + + #region Flying + + if (actor != null && actor.Flying) + { + m_animTickFall = 0; + m_animTickJump = 0; + + if (move.X != 0f || move.Y != 0f) + { + return (m_useFlySlow ? "FLYSLOW" : "FLY"); + } + else if (move.Z > 0f) + { + return "HOVER_UP"; + } + else if (move.Z < 0f) + { + if (actor != null && actor.IsColliding) + return "LAND"; + else + return "HOVER_DOWN"; + } + else + { + return "HOVER"; + } + } + + #endregion Flying + + #region Falling/Floating/Landing + + if (actor == null || !actor.IsColliding) + { + float fallElapsed = (float)(Environment.TickCount - m_animTickFall) / 1000f; + + if (m_animTickFall == 0 || (fallElapsed > FALL_DELAY && actor.Velocity.Z >= 0.0f)) + { + // Just started falling + m_animTickFall = Environment.TickCount; + } + else if (!jumping && fallElapsed > FALL_DELAY) + { + // Falling long enough to trigger the animation + return "FALLDOWN"; + } + + return m_movementAnimation; + } + + #endregion Falling/Floating/Landing + + #region Ground Movement + + if (m_movementAnimation == "FALLDOWN") + { + m_animTickFall = Environment.TickCount; + + // TODO: SOFT_LAND support + return "LAND"; + } + else if (m_movementAnimation == "LAND") + { + float landElapsed = (float)(Environment.TickCount - m_animTickFall) / 1000f; + + if (landElapsed <= FALL_DELAY) + return "LAND"; + } + + m_animTickFall = 0; + + if (move.Z > 0f) + { + // Jumping + if (!jumping) + { + // Begin prejump + m_animTickJump = Environment.TickCount; + return "PREJUMP"; + } + else if (Environment.TickCount - m_animTickJump > PREJUMP_DELAY * 1000.0f) + { + // Start actual jump + if (m_animTickJump == -1) + { + // Already jumping! End the current jump + m_animTickJump = 0; + return "JUMP"; + } + + m_animTickJump = -1; + return "JUMP"; + } + } + else + { + // Not jumping + m_animTickJump = 0; + + if (move.X != 0f || move.Y != 0f) + { + // Walking / crouchwalking / running + if (move.Z < 0f) + return "CROUCHWALK"; + else if (m_setAlwaysRun) + return "RUN"; + else + return "WALK"; + } + else + { + // Not walking + if (move.Z < 0f) + return "CROUCH"; + else + return "STAND"; + } + } + + #endregion Ground Movement + + return m_movementAnimation; + } + /// /// Update the movement animation of this avatar according to its current state /// protected void UpdateMovementAnimations() { - string movementAnimation = GetMovementAnimation(); + string movementAnimation = GetMovementAnimation2(); if (movementAnimation == "FALLDOWN" && m_allowFalling == false) { @@ -2367,7 +2533,8 @@ namespace OpenSim.Region.Framework.Scenes if (m_isChildAgent == false) { - Vector3 velocity = (m_physicsActor != null) ? m_physicsActor.Velocity : Vector3.Zero; + PhysicsActor actor = m_physicsActor; + Vector3 velocity = (actor != null) ? actor.Velocity : Vector3.Zero; // Throw away duplicate or insignificant updates if (!m_bodyRot.ApproxEquals(m_lastRotation, ROTATION_TOLERANCE) || -- cgit v1.1 From 5c894dac8bc99c92a806f0ebc882684fdb76da80 Mon Sep 17 00:00:00 2001 From: John Hurliman Date: Thu, 29 Oct 2009 05:34:40 -0700 Subject: * Implemented foot collision plane for avatars * Fixed a NullReferenceException regression --- OpenSim/Region/Framework/Scenes/ScenePresence.cs | 259 ++++------------------- 1 file changed, 44 insertions(+), 215 deletions(-) (limited to 'OpenSim/Region/Framework/Scenes/ScenePresence.cs') diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index c4f4021..e510f75 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -91,6 +91,7 @@ namespace OpenSim.Region.Framework.Scenes //private SceneObjectPart proxyObjectPart = null; public Vector3 lastKnownAllowedPosition; public bool sentMessageAboutRestrictedParcelFlyingDown; + public Vector4 CollisionPlane = Vector4.UnitW; private Vector3 m_lastPosition; private Quaternion m_lastRotation; @@ -130,10 +131,8 @@ namespace OpenSim.Region.Framework.Scenes private bool m_setAlwaysRun; private string m_movementAnimation = "DEFAULT"; - private long m_animPersistUntil; private int m_animTickFall; private int m_animTickJump; - private bool m_allowFalling; private bool m_useFlySlow; private bool m_usePreJump; private bool m_forceFly; @@ -2045,208 +2044,10 @@ namespace OpenSim.Region.Framework.Scenes /// public string GetMovementAnimation() { - if ((m_animPersistUntil > 0) && (m_animPersistUntil > DateTime.Now.Ticks)) - { - //We don't want our existing state to end yet. - return m_movementAnimation; - - } - else if (m_movementflag != 0) - { - //We're moving - m_allowFalling = true; - if (PhysicsActor != null && PhysicsActor.IsColliding) - { - //And colliding. Can you guess what it is yet? - if ((m_movementflag & (uint)AgentManager.ControlFlags.AGENT_CONTROL_UP_NEG) != 0) - { - //Down key is being pressed. - if ((m_movementflag & (uint)AgentManager.ControlFlags.AGENT_CONTROL_AT_NEG) + (m_movementflag & (uint)AgentManager.ControlFlags.AGENT_CONTROL_AT_POS) != 0) - { - return "CROUCHWALK"; - } - else - { - return "CROUCH"; - } - } - else if (m_setAlwaysRun) - { - return "RUN"; - } - else - { - //If we're prejumping then inhibit this, it's a problem - //caused by a false positive on IsColliding - if (m_movementAnimation == "PREJUMP") - { - return "PREJUMP"; - } - else - { - return "WALK"; - } - } - - } - else - { - //We're not colliding. Colliding isn't cool these days. - if (PhysicsActor != null && PhysicsActor.Flying) - { - //Are we moving forwards or backwards? - if ((m_movementflag & (uint)AgentManager.ControlFlags.AGENT_CONTROL_AT_POS) != 0 || (m_movementflag & (uint)AgentManager.ControlFlags.AGENT_CONTROL_AT_NEG) != 0) - { - //Then we really are flying - if (m_setAlwaysRun) - { - return "FLY"; - } - else - { - if (m_useFlySlow == false) - { - return "FLY"; - } - else - { - return "FLYSLOW"; - } - } - } - else - { - if ((m_movementflag & (uint)AgentManager.ControlFlags.AGENT_CONTROL_UP_POS) != 0) - { - return "HOVER_UP"; - } - else - { - return "HOVER_DOWN"; - } - } - - } - else if (m_movementAnimation == "JUMP") - { - //If we were already jumping, continue to jump until we collide - return "JUMP"; - - } - else if (m_movementAnimation == "PREJUMP" && (m_movementflag & (uint)AgentManager.ControlFlags.AGENT_CONTROL_UP_POS) == 0) - { - //If we were in a prejump, and the UP key is no longer being held down - //then we're not going to fly, so we're jumping - return "JUMP"; - - } - else if ((m_movementflag & (uint)AgentManager.ControlFlags.AGENT_CONTROL_UP_POS) != 0) - { - //They're pressing up, so we're either going to fly or jump - return "PREJUMP"; - } - else - { - //If we're moving and not flying and not jumping and not colliding.. - - if (m_movementAnimation == "WALK" || m_movementAnimation == "RUN") - { - //Let's not enter a FALLDOWN state here, since we're probably - //not colliding because we're going down hill. - return m_movementAnimation; - } - //Record the time we enter this state so we know whether to "land" or not - m_animPersistUntil = DateTime.Now.Ticks; - return "FALLDOWN"; - - } - } - } - else - { - //We're not moving. - if (PhysicsActor != null && PhysicsActor.IsColliding) - { - //But we are colliding. - if (m_movementAnimation == "FALLDOWN") - { - //We're re-using the m_animPersistUntil value here to see how long we've been falling - if ((DateTime.Now.Ticks - m_animPersistUntil) > TimeSpan.TicksPerSecond) - { - //Make sure we don't change state for a bit - m_animPersistUntil = DateTime.Now.Ticks + TimeSpan.TicksPerSecond; - return "LAND"; - } - else - { - //We haven't been falling very long, we were probably just walking down hill - return "STAND"; - } - } - else if (m_movementAnimation == "JUMP" || m_movementAnimation == "HOVER_DOWN") - { - //Make sure we don't change state for a bit - m_animPersistUntil = DateTime.Now.Ticks + (1 * TimeSpan.TicksPerSecond); - return "SOFT_LAND"; - - } - else if ((m_movementflag & (uint)AgentManager.ControlFlags.AGENT_CONTROL_UP_POS) != 0) - { - return "PREJUMP"; - } - else if (PhysicsActor != null && PhysicsActor.Flying) - { - m_allowFalling = true; - if ((m_movementflag & (uint)AgentManager.ControlFlags.AGENT_CONTROL_UP_POS) != 0) - { - return "HOVER_UP"; - } - else if ((m_movementflag & (uint)AgentManager.ControlFlags.AGENT_CONTROL_UP_NEG) != 0) - { - return "HOVER_DOWN"; - } - else - { - return "HOVER"; - } - } - else - { - return "STAND"; - } - - } - else - { - //We're not colliding. - if (PhysicsActor != null && PhysicsActor.Flying) - { - - return "HOVER"; - - } - else if ((m_movementAnimation == "JUMP" || m_movementAnimation == "PREJUMP") && (m_movementflag & (uint)AgentManager.ControlFlags.AGENT_CONTROL_UP_POS) == 0) - { - - return "JUMP"; - - } - else - { - //Record the time we enter this state so we know whether to "land" or not - m_animPersistUntil = DateTime.Now.Ticks; - return "FALLDOWN"; // this falling animation is invoked too frequently when capsule tilt correction is used - why? - } - } - } - } - - public string GetMovementAnimation2() - { const float FALL_DELAY = 0.33f; const float PREJUMP_DELAY = 0.25f; - m_allowFalling = true; + #region Inputs AgentManager.ControlFlags controlFlags = (AgentManager.ControlFlags)m_AgentControlFlags; PhysicsActor actor = m_physicsActor; @@ -2281,6 +2082,8 @@ namespace OpenSim.Region.Framework.Scenes bool moving = (move != Vector3.Zero); bool jumping = m_animTickJump != 0; + #endregion Inputs + #region Flying if (actor != null && actor.Flying) @@ -2410,24 +2213,16 @@ namespace OpenSim.Region.Framework.Scenes /// protected void UpdateMovementAnimations() { - string movementAnimation = GetMovementAnimation2(); - - if (movementAnimation == "FALLDOWN" && m_allowFalling == false) - { - movementAnimation = m_movementAnimation; - } - else - { - m_movementAnimation = movementAnimation; - } - if (movementAnimation == "PREJUMP" && m_usePreJump == false) + m_movementAnimation = GetMovementAnimation(); + + if (m_movementAnimation == "PREJUMP" && !m_usePreJump) { - //This was the previous behavior before PREJUMP + // This was the previous behavior before PREJUMP TrySetMovementAnimation("JUMP"); } else { - TrySetMovementAnimation(movementAnimation); + TrySetMovementAnimation(m_movementAnimation); } } @@ -2574,13 +2369,16 @@ namespace OpenSim.Region.Framework.Scenes { m_perfMonMS = Environment.TickCount; + PhysicsActor actor = m_physicsActor; + Vector3 velocity = (actor != null) ? actor.Velocity : Vector3.Zero; + Vector3 pos = m_pos; pos.Z += m_appearance.HipOffset; //m_log.DebugFormat("[SCENEPRESENCE]: TerseUpdate: Pos={0} Rot={1} Vel={2}", m_pos, m_bodyRot, m_velocity); remoteClient.SendAvatarTerseUpdate(new SendAvatarTerseData(m_regionHandle, (ushort)(m_scene.TimeDilation * ushort.MaxValue), LocalId, - pos, m_physicsActor.Velocity, Vector3.Zero, m_bodyRot, Vector4.UnitW, m_uuid, null, GetUpdatePriority(remoteClient))); + pos, velocity, Vector3.Zero, m_bodyRot, CollisionPlane, m_uuid, null, GetUpdatePriority(remoteClient))); m_scene.StatsReporter.AddAgentTime(Environment.TickCount - m_perfMonMS); m_scene.StatsReporter.AddAgentUpdates(1); @@ -3527,6 +3325,37 @@ namespace OpenSim.Region.Framework.Scenes CollisionEventUpdate collisionData = (CollisionEventUpdate)e; Dictionary coldata = collisionData.m_objCollisionList; + CollisionPlane = Vector4.UnitW; + + if (coldata.Count != 0) + { + switch (m_movementAnimation) + { + case "STAND": + case "WALK": + case "RUN": + case "CROUCH": + case "CROUCHWALK": + { + ContactPoint lowest; + lowest.SurfaceNormal = Vector3.Zero; + lowest.Position = Vector3.Zero; + lowest.Position.Z = Single.NaN; + + foreach (ContactPoint contact in coldata.Values) + { + if (Single.IsNaN(lowest.Position.Z) || contact.Position.Z < lowest.Position.Z) + { + lowest = contact; + } + } + + CollisionPlane = new Vector4(-lowest.SurfaceNormal, -Vector3.Dot(lowest.Position, lowest.SurfaceNormal)); + } + break; + } + } + if (m_invulnerable) return; -- cgit v1.1 From 2913c24c8a5a4a50e9267aa125abcc7956a388d1 Mon Sep 17 00:00:00 2001 From: John Hurliman Date: Thu, 29 Oct 2009 15:24:31 -0700 Subject: * Commented out two noisy debug lines in the LLUDP server * Misc. cleanup in ScenePresence.HandleAgentUpdate() --- OpenSim/Region/Framework/Scenes/ScenePresence.cs | 263 +++++++++++------------ 1 file changed, 124 insertions(+), 139 deletions(-) (limited to 'OpenSim/Region/Framework/Scenes/ScenePresence.cs') diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index e510f75..04c22d0 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -76,7 +76,9 @@ namespace OpenSim.Region.Framework.Scenes private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); private static readonly byte[] BAKE_INDICES = new byte[] { 8, 9, 10, 11, 19, 20 }; - public static readonly byte[] DEFAULT_TEXTURE = AvatarAppearance.GetDefaultTexture().GetBytes(); + private static readonly byte[] DEFAULT_TEXTURE = AvatarAppearance.GetDefaultTexture().GetBytes(); + private static readonly Array DIR_CONTROL_FLAGS = Enum.GetValues(typeof(Dir_ControlFlags)); + private static readonly Vector3 HEAD_ADJUSTMENT = new Vector3(0f, 0f, 0.3f); public UUID currentParcelUUID = UUID.Zero; @@ -171,7 +173,7 @@ namespace OpenSim.Region.Framework.Scenes protected Vector3 m_CameraAtAxis; protected Vector3 m_CameraLeftAxis; protected Vector3 m_CameraUpAxis; - private uint m_AgentControlFlags; + private AgentManager.ControlFlags m_AgentControlFlags; private Quaternion m_headrotation = Quaternion.Identity; private byte m_state; @@ -380,8 +382,8 @@ namespace OpenSim.Region.Framework.Scenes public uint AgentControlFlags { - get { return m_AgentControlFlags; } - set { m_AgentControlFlags = value; } + get { return (uint)m_AgentControlFlags; } + set { m_AgentControlFlags = (AgentManager.ControlFlags)value; } } /// @@ -707,25 +709,25 @@ namespace OpenSim.Region.Framework.Scenes private void SetDirectionVectors() { - Dir_Vectors[0] = new Vector3(1, 0, 0); //FORWARD - Dir_Vectors[1] = new Vector3(-1, 0, 0); //BACK - Dir_Vectors[2] = new Vector3(0, 1, 0); //LEFT - Dir_Vectors[3] = new Vector3(0, -1, 0); //RIGHT - Dir_Vectors[4] = new Vector3(0, 0, 1); //UP - Dir_Vectors[5] = new Vector3(0, 0, -1); //DOWN - Dir_Vectors[5] = new Vector3(0, 0, -0.5f); //DOWN_Nudge + Dir_Vectors[0] = Vector3.UnitX; //FORWARD + Dir_Vectors[1] = -Vector3.UnitX; //BACK + Dir_Vectors[2] = Vector3.UnitY; //LEFT + Dir_Vectors[3] = -Vector3.UnitY; //RIGHT + Dir_Vectors[4] = Vector3.UnitZ; //UP + Dir_Vectors[5] = -Vector3.UnitZ; //DOWN + Dir_Vectors[5] = new Vector3(0f, 0f, -0.5f); //DOWN_Nudge } private Vector3[] GetWalkDirectionVectors() { Vector3[] vector = new Vector3[6]; - vector[0] = new Vector3(m_CameraUpAxis.Z, 0, -m_CameraAtAxis.Z); //FORWARD - vector[1] = new Vector3(-m_CameraUpAxis.Z, 0, m_CameraAtAxis.Z); //BACK - vector[2] = new Vector3(0, 1, 0); //LEFT - vector[3] = new Vector3(0, -1, 0); //RIGHT - vector[4] = new Vector3(m_CameraAtAxis.Z, 0, m_CameraUpAxis.Z); //UP - vector[5] = new Vector3(-m_CameraAtAxis.Z, 0, -m_CameraUpAxis.Z); //DOWN - vector[5] = new Vector3(-m_CameraAtAxis.Z, 0, -m_CameraUpAxis.Z); //DOWN_Nudge + vector[0] = new Vector3(m_CameraUpAxis.Z, 0f, -m_CameraAtAxis.Z); //FORWARD + vector[1] = new Vector3(-m_CameraUpAxis.Z, 0f, m_CameraAtAxis.Z); //BACK + vector[2] = Vector3.UnitY; //LEFT + vector[3] = -Vector3.UnitY; //RIGHT + vector[4] = new Vector3(m_CameraAtAxis.Z, 0f, m_CameraUpAxis.Z); //UP + vector[5] = new Vector3(-m_CameraAtAxis.Z, 0f, -m_CameraUpAxis.Z); //DOWN + vector[5] = new Vector3(-m_CameraAtAxis.Z, 0f, -m_CameraUpAxis.Z); //DOWN_Nudge return vector; } @@ -1074,7 +1076,7 @@ namespace OpenSim.Region.Framework.Scenes } m_isChildAgent = false; - bool m_flying = ((m_AgentControlFlags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_FLY) != 0); + bool m_flying = ((m_AgentControlFlags & AgentManager.ControlFlags.AGENT_CONTROL_FLY) != 0); MakeRootAgent(AbsolutePosition, m_flying); if ((m_callbackURI != null) && !m_callbackURI.Equals("")) @@ -1101,9 +1103,12 @@ namespace OpenSim.Region.Framework.Scenes /// public void RayCastCameraCallback(bool hitYN, Vector3 collisionPoint, uint localid, float distance) { + const float POSITION_TOLERANCE = 0.02f; + const float VELOCITY_TOLERANCE = 0.02f; + const float ROTATION_TOLERANCE = 0.02f; + if (m_followCamAuto) { - if (hitYN) { CameraConstraintActive = true; @@ -1112,11 +1117,11 @@ namespace OpenSim.Region.Framework.Scenes Vector3 normal = Vector3.Normalize(new Vector3(0f, 0f, collisionPoint.Z) - collisionPoint); ControllingClient.SendCameraConstraint(new Vector4(normal.X, normal.Y, normal.Z, -1 * Vector3.Distance(new Vector3(0,0,collisionPoint.Z),collisionPoint))); } - else + else { - if ((m_pos - m_lastPosition).Length() > 0.02f || - (m_velocity - m_lastVelocity).Length() > 0.02f || - m_bodyRot != m_lastRotation) + if (!m_pos.ApproxEquals(m_lastPosition, POSITION_TOLERANCE) || + !m_velocity.ApproxEquals(m_lastVelocity, VELOCITY_TOLERANCE) || + !m_bodyRot.ApproxEquals(m_lastRotation, ROTATION_TOLERANCE)) { if (CameraConstraintActive) { @@ -1125,13 +1130,11 @@ namespace OpenSim.Region.Framework.Scenes } } } - } + } } - Array m_dirControlFlags = Enum.GetValues(typeof(Dir_ControlFlags)); - /// - /// This is the event handler for client movement. If a client is moving, this event is triggering. + /// This is the event handler for client movement. If a client is moving, this event is triggering. /// public void HandleAgentUpdate(IClientAPI remoteClient, AgentUpdateArgs agentData) { @@ -1147,15 +1150,13 @@ namespace OpenSim.Region.Framework.Scenes if (m_movementUpdateCount < 1) m_movementUpdateCount = 1; - // Must check for standing up even when PhysicsActor is null, - // since sitting currently removes avatar from physical scene - //m_log.Debug("agentPos:" + AbsolutePosition.ToString()); + #region Sanity Checking // This is irritating. Really. if (!AbsolutePosition.IsFinite()) { RemoveFromPhysicalScene(); - m_log.Error("[AVATAR]: NonFinite Avatar position detected... Reset Position. Mantis this please. Error# 9999902"); + m_log.Error("[AVATAR]: NonFinite Avatar position detected... Reset Position. Mantis this please. Error #9999902"); m_pos = m_LastFinitePos; if (!m_pos.IsFinite()) @@ -1163,7 +1164,7 @@ namespace OpenSim.Region.Framework.Scenes m_pos.X = 127f; m_pos.Y = 127f; m_pos.Z = 127f; - m_log.Error("[AVATAR]: NonFinite Avatar position detected... Reset Position. Mantis this please. Error# 9999903"); + m_log.Error("[AVATAR]: NonFinite Avatar position detected... Reset Position. Mantis this please. Error #9999903"); } AddToPhysicalScene(false); @@ -1173,18 +1174,11 @@ namespace OpenSim.Region.Framework.Scenes m_LastFinitePos = m_pos; } - //m_physicsActor.AddForce(new PhysicsVector(999999999, 99999999, 999999999999999), true); + #endregion Sanity Checking - //ILandObject land = LandChannel.GetLandObject(agent.startpos.X, agent.startpos.Y); - //if (land != null) - //{ - //if (land.landData.landingType == (byte)1 && land.landData.userLocation != Vector3.Zero) - //{ - // agent.startpos = land.landData.userLocation; - //} - //} + #region Inputs - uint flags = agentData.ControlFlags; + AgentManager.ControlFlags flags = (AgentManager.ControlFlags)agentData.ControlFlags; Quaternion bodyRotation = agentData.BodyRotation; // Camera location in world. We'll need to raytrace @@ -1205,87 +1199,85 @@ namespace OpenSim.Region.Framework.Scenes // The Agent's Draw distance setting m_DrawDistance = agentData.Far; - if ((flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_STAND_UP) != 0) - { - StandUp(); - } - // Check if Client has camera in 'follow cam' or 'build' mode. Vector3 camdif = (Vector3.One * m_bodyRot - Vector3.One * CameraRotation); m_followCamAuto = ((m_CameraUpAxis.Z > 0.959f && m_CameraUpAxis.Z < 0.98f) && (Math.Abs(camdif.X) < 0.4f && Math.Abs(camdif.Y) < 0.4f)) ? true : false; + m_mouseLook = (flags & AgentManager.ControlFlags.AGENT_CONTROL_MOUSELOOK) != 0; + m_leftButtonDown = (flags & AgentManager.ControlFlags.AGENT_CONTROL_LBUTTON_DOWN) != 0; + + #endregion Inputs + + if ((flags & AgentManager.ControlFlags.AGENT_CONTROL_STAND_UP) != 0) + { + StandUp(); + } + //m_log.DebugFormat("[FollowCam]: {0}", m_followCamAuto); // Raycast from the avatar's head to the camera to see if there's anything blocking the view if ((m_movementUpdateCount % NumMovementsBetweenRayCast) == 0 && m_scene.PhysicsScene.SupportsRayCast()) { if (m_followCamAuto) { - Vector3 headadjustment = new Vector3(0, 0, 0.3f); - m_scene.PhysicsScene.RaycastWorld(m_pos, Vector3.Normalize(m_CameraCenter - (m_pos + headadjustment)), Vector3.Distance(m_CameraCenter, (m_pos + headadjustment)) + 0.3f, RayCastCameraCallback); + Vector3 posAdjusted = m_pos + HEAD_ADJUSTMENT; + m_scene.PhysicsScene.RaycastWorld(m_pos, Vector3.Normalize(m_CameraCenter - posAdjusted), Vector3.Distance(m_CameraCenter, posAdjusted) + 0.3f, RayCastCameraCallback); } } - m_mouseLook = (flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_MOUSELOOK) != 0; - m_leftButtonDown = (flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_LBUTTON_DOWN) != 0; - lock (scriptedcontrols) { if (scriptedcontrols.Count > 0) { - SendControlToScripts(flags); + SendControlToScripts((uint)flags); flags = RemoveIgnoredControls(flags, IgnoredControls); } } - if (PhysicsActor == null) - { - return; - } - if (m_autopilotMoving) CheckAtSitTarget(); - if ((flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_SIT_ON_GROUND) != 0) + if ((flags & AgentManager.ControlFlags.AGENT_CONTROL_SIT_ON_GROUND) != 0) { // TODO: This doesn't prevent the user from walking yet. // Setting parent ID would fix this, if we knew what value // to use. Or we could add a m_isSitting variable. - TrySetMovementAnimation("SIT_GROUND_CONSTRAINED"); } + // In the future, these values might need to go global. // Here's where you get them. - m_AgentControlFlags = flags; m_headrotation = agentData.HeadRotation; m_state = agentData.State; + PhysicsActor actor = PhysicsActor; + if (actor == null) + { + return; + } + if (m_allowMovement) { int i = 0; bool update_movementflag = false; bool update_rotation = false; bool DCFlagKeyPressed = false; - Vector3 agent_control_v3 = new Vector3(0, 0, 0); + Vector3 agent_control_v3 = Vector3.Zero; Quaternion q = bodyRotation; - if (PhysicsActor != null) - { - bool oldflying = PhysicsActor.Flying; - if (m_forceFly) - PhysicsActor.Flying = true; - else if (m_flyDisabled) - PhysicsActor.Flying = false; - else - PhysicsActor.Flying = ((flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_FLY) != 0); + bool oldflying = PhysicsActor.Flying; - if (PhysicsActor.Flying != oldflying) - { - update_movementflag = true; - } - } + if (m_forceFly) + actor.Flying = true; + else if (m_flyDisabled) + actor.Flying = false; + else + actor.Flying = ((flags & AgentManager.ControlFlags.AGENT_CONTROL_FLY) != 0); + + if (actor.Flying != oldflying) + update_movementflag = true; if (q != m_bodyRot) { @@ -1307,10 +1299,9 @@ namespace OpenSim.Region.Framework.Scenes else dirVectors = Dir_Vectors; - - foreach (Dir_ControlFlags DCF in m_dirControlFlags) + foreach (Dir_ControlFlags DCF in DIR_CONTROL_FLAGS) { - if ((flags & (uint)DCF) != 0) + if (((uint)flags & (uint)DCF) != 0) { bResetMoveToPosition = true; DCFlagKeyPressed = true; @@ -1356,7 +1347,7 @@ namespace OpenSim.Region.Framework.Scenes if (bAllowUpdateMoveToPosition && (m_moveToPositionInProgress && !m_autopilotMoving)) { //Check the error term of the current position in relation to the target position - if (Util.GetDistanceTo(AbsolutePosition, m_moveToPositionTarget) <= 1.5) + if (Util.GetDistanceTo(AbsolutePosition, m_moveToPositionTarget) <= 1.5f) { // we are close enough to the target m_moveToPositionTarget = Vector3.Zero; @@ -1437,8 +1428,8 @@ namespace OpenSim.Region.Framework.Scenes if (m_physicsActor != null && m_physicsActor.Flying && !m_forceFly) { // Are the landing controls requirements filled? - bool controlland = (((flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_UP_NEG) != 0) || - ((flags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_UP_NEG) != 0)); + bool controlland = (((flags & AgentManager.ControlFlags.AGENT_CONTROL_UP_NEG) != 0) || + ((flags & AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_UP_NEG) != 0)); // Are the collision requirements fulfilled? bool colliding = (m_physicsActor.IsColliding == true); @@ -1605,7 +1596,7 @@ namespace OpenSim.Region.Framework.Scenes } m_pos += m_parentPosition + new Vector3(0.0f, 0.0f, 2.0f*m_sitAvatarHeight); - m_parentPosition = new Vector3(); + m_parentPosition = Vector3.Zero; m_parentID = 0; SendFullUpdateToAllClients(); @@ -2776,11 +2767,8 @@ namespace OpenSim.Region.Framework.Scenes agentpos.CopyFrom(cadu); m_scene.SendOutChildAgentUpdates(agentpos, this); - - m_LastChildAgentUpdatePosition.X = AbsolutePosition.X; - m_LastChildAgentUpdatePosition.Y = AbsolutePosition.Y; - m_LastChildAgentUpdatePosition.Z = AbsolutePosition.Z; + m_LastChildAgentUpdatePosition = AbsolutePosition; } } @@ -2905,9 +2893,9 @@ namespace OpenSim.Region.Framework.Scenes m_inTransit = true; if ((m_physicsActor != null) && m_physicsActor.Flying) - m_AgentControlFlags |= (uint)AgentManager.ControlFlags.AGENT_CONTROL_FLY; - else if ((m_AgentControlFlags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_FLY) != 0) - m_AgentControlFlags &= ~(uint)AgentManager.ControlFlags.AGENT_CONTROL_FLY; + m_AgentControlFlags |= AgentManager.ControlFlags.AGENT_CONTROL_FLY; + else if ((m_AgentControlFlags & AgentManager.ControlFlags.AGENT_CONTROL_FLY) != 0) + m_AgentControlFlags &= ~AgentManager.ControlFlags.AGENT_CONTROL_FLY; } public void NotInTransit() @@ -2923,7 +2911,7 @@ namespace OpenSim.Region.Framework.Scenes public void Reset() { // Put the child agent back at the center - AbsolutePosition = new Vector3(((int)Constants.RegionSize * 0.5f), ((int)Constants.RegionSize * 0.5f), 70); + AbsolutePosition = new Vector3(((float)Constants.RegionSize * 0.5f), ((float)Constants.RegionSize * 0.5f), 70); ResetAnimations(); } @@ -3093,7 +3081,7 @@ namespace OpenSim.Region.Framework.Scenes cAgent.HeadRotation = m_headrotation; cAgent.BodyRotation = m_bodyRot; - cAgent.ControlFlags = m_AgentControlFlags; + cAgent.ControlFlags = (uint)m_AgentControlFlags; if (m_scene.Permissions.IsGod(new UUID(cAgent.AgentID))) cAgent.GodLevel = (byte)m_godlevel; @@ -3181,7 +3169,7 @@ namespace OpenSim.Region.Framework.Scenes m_headrotation = cAgent.HeadRotation; m_bodyRot = cAgent.BodyRotation; - m_AgentControlFlags = cAgent.ControlFlags; + m_AgentControlFlags = (AgentManager.ControlFlags)cAgent.ControlFlags; if (m_scene.Permissions.IsGod(new UUID(cAgent.AgentID))) m_godlevel = cAgent.GodLevel; @@ -3594,19 +3582,10 @@ namespace OpenSim.Region.Framework.Scenes IgnoredControls &= ~(ScriptControlled)controls; if (scriptedcontrols.ContainsKey(Script_item_UUID)) scriptedcontrols.Remove(Script_item_UUID); - } else { - - if (scriptedcontrols.ContainsKey(Script_item_UUID)) - { - scriptedcontrols[Script_item_UUID] = obj; - } - else - { - scriptedcontrols.Add(Script_item_UUID, obj); - } + scriptedcontrols[Script_item_UUID] = obj; } } ControllingClient.SendTakeControls(controls, pass_on == 1 ? true : false, true); @@ -3624,12 +3603,14 @@ namespace OpenSim.Region.Framework.Scenes public void UnRegisterControlEventsToScript(uint Obj_localID, UUID Script_item_UUID) { + ScriptControllers takecontrols; + lock (scriptedcontrols) { - if (scriptedcontrols.ContainsKey(Script_item_UUID)) + if (scriptedcontrols.TryGetValue(Script_item_UUID, out takecontrols)) { - ScriptControllers takecontrolls = scriptedcontrols[Script_item_UUID]; - ScriptControlled sctc = takecontrolls.eventControls; + ScriptControlled sctc = takecontrols.eventControls; + ControllingClient.SendTakeControls((int)sctc, false, false); ControllingClient.SendTakeControls((int)sctc, true, false); @@ -3640,7 +3621,6 @@ namespace OpenSim.Region.Framework.Scenes IgnoredControls |= scData.ignoreControls; } } - } } @@ -3707,9 +3687,11 @@ namespace OpenSim.Region.Framework.Scenes { lock (scriptedcontrols) { - foreach (UUID scriptUUID in scriptedcontrols.Keys) + foreach (KeyValuePair kvp in scriptedcontrols) { - ScriptControllers scriptControlData = scriptedcontrols[scriptUUID]; + UUID scriptUUID = kvp.Key; + ScriptControllers scriptControlData = kvp.Value; + ScriptControlled localHeld = allflags & scriptControlData.eventControls; // the flags interesting for us ScriptControlled localLast = LastCommands & scriptControlData.eventControls; // the activated controls in the last cycle ScriptControlled localChange = localHeld ^ localLast; // the changed bits @@ -3725,37 +3707,40 @@ namespace OpenSim.Region.Framework.Scenes LastCommands = allflags; } - internal static uint RemoveIgnoredControls(uint flags, ScriptControlled Ignored) + internal static AgentManager.ControlFlags RemoveIgnoredControls(AgentManager.ControlFlags flags, ScriptControlled ignored) { - if (Ignored == ScriptControlled.CONTROL_ZERO) + if (ignored == ScriptControlled.CONTROL_ZERO) return flags; - if ((Ignored & ScriptControlled.CONTROL_BACK) != 0) - flags &= ~((uint)AgentManager.ControlFlags.AGENT_CONTROL_AT_NEG | (uint)AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_AT_NEG); - if ((Ignored & ScriptControlled.CONTROL_FWD) != 0) - flags &= ~((uint)AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_AT_POS | (uint)AgentManager.ControlFlags.AGENT_CONTROL_AT_POS); - if ((Ignored & ScriptControlled.CONTROL_DOWN) != 0) - flags &= ~((uint)AgentManager.ControlFlags.AGENT_CONTROL_UP_NEG | (uint)AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_UP_NEG); - if ((Ignored & ScriptControlled.CONTROL_UP) != 0) - flags &= ~((uint)AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_UP_POS | (uint)AgentManager.ControlFlags.AGENT_CONTROL_UP_POS); - if ((Ignored & ScriptControlled.CONTROL_LEFT) != 0) - flags &= ~((uint)AgentManager.ControlFlags.AGENT_CONTROL_LEFT_POS | (uint)AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_LEFT_POS); - if ((Ignored & ScriptControlled.CONTROL_RIGHT) != 0) - flags &= ~((uint)AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_LEFT_NEG | (uint)AgentManager.ControlFlags.AGENT_CONTROL_LEFT_NEG); - if ((Ignored & ScriptControlled.CONTROL_ROT_LEFT) != 0) - flags &= ~((uint)AgentManager.ControlFlags.AGENT_CONTROL_YAW_NEG); - if ((Ignored & ScriptControlled.CONTROL_ROT_RIGHT) != 0) - flags &= ~((uint)AgentManager.ControlFlags.AGENT_CONTROL_YAW_POS); - if ((Ignored & ScriptControlled.CONTROL_ML_LBUTTON) != 0) - flags &= ~((uint)AgentManager.ControlFlags.AGENT_CONTROL_ML_LBUTTON_DOWN); - if ((Ignored & ScriptControlled.CONTROL_LBUTTON) != 0) - flags &= ~((uint)AgentManager.ControlFlags.AGENT_CONTROL_LBUTTON_UP | (uint)AgentManager.ControlFlags.AGENT_CONTROL_LBUTTON_DOWN); - //DIR_CONTROL_FLAG_FORWARD = AgentManager.ControlFlags.AGENT_CONTROL_AT_POS, - //DIR_CONTROL_FLAG_BACK = AgentManager.ControlFlags.AGENT_CONTROL_AT_NEG, - //DIR_CONTROL_FLAG_LEFT = AgentManager.ControlFlags.AGENT_CONTROL_LEFT_POS, - //DIR_CONTROL_FLAG_RIGHT = AgentManager.ControlFlags.AGENT_CONTROL_LEFT_NEG, - //DIR_CONTROL_FLAG_UP = AgentManager.ControlFlags.AGENT_CONTROL_UP_POS, - //DIR_CONTROL_FLAG_DOWN = AgentManager.ControlFlags.AGENT_CONTROL_UP_NEG, - //DIR_CONTROL_FLAG_DOWN_NUDGE = AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_UP_NEG + + if ((ignored & ScriptControlled.CONTROL_BACK) != 0) + flags &= ~(AgentManager.ControlFlags.AGENT_CONTROL_AT_NEG | AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_AT_NEG); + if ((ignored & ScriptControlled.CONTROL_FWD) != 0) + flags &= ~(AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_AT_POS | AgentManager.ControlFlags.AGENT_CONTROL_AT_POS); + if ((ignored & ScriptControlled.CONTROL_DOWN) != 0) + flags &= ~(AgentManager.ControlFlags.AGENT_CONTROL_UP_NEG | AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_UP_NEG); + if ((ignored & ScriptControlled.CONTROL_UP) != 0) + flags &= ~(AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_UP_POS | AgentManager.ControlFlags.AGENT_CONTROL_UP_POS); + if ((ignored & ScriptControlled.CONTROL_LEFT) != 0) + flags &= ~(AgentManager.ControlFlags.AGENT_CONTROL_LEFT_POS | AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_LEFT_POS); + if ((ignored & ScriptControlled.CONTROL_RIGHT) != 0) + flags &= ~(AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_LEFT_NEG | AgentManager.ControlFlags.AGENT_CONTROL_LEFT_NEG); + if ((ignored & ScriptControlled.CONTROL_ROT_LEFT) != 0) + flags &= ~(AgentManager.ControlFlags.AGENT_CONTROL_YAW_NEG); + if ((ignored & ScriptControlled.CONTROL_ROT_RIGHT) != 0) + flags &= ~(AgentManager.ControlFlags.AGENT_CONTROL_YAW_POS); + if ((ignored & ScriptControlled.CONTROL_ML_LBUTTON) != 0) + flags &= ~(AgentManager.ControlFlags.AGENT_CONTROL_ML_LBUTTON_DOWN); + if ((ignored & ScriptControlled.CONTROL_LBUTTON) != 0) + flags &= ~(AgentManager.ControlFlags.AGENT_CONTROL_LBUTTON_UP | AgentManager.ControlFlags.AGENT_CONTROL_LBUTTON_DOWN); + + //DIR_CONTROL_FLAG_FORWARD = AgentManager.ControlFlags.AGENT_CONTROL_AT_POS, + //DIR_CONTROL_FLAG_BACK = AgentManager.ControlFlags.AGENT_CONTROL_AT_NEG, + //DIR_CONTROL_FLAG_LEFT = AgentManager.ControlFlags.AGENT_CONTROL_LEFT_POS, + //DIR_CONTROL_FLAG_RIGHT = AgentManager.ControlFlags.AGENT_CONTROL_LEFT_NEG, + //DIR_CONTROL_FLAG_UP = AgentManager.ControlFlags.AGENT_CONTROL_UP_POS, + //DIR_CONTROL_FLAG_DOWN = AgentManager.ControlFlags.AGENT_CONTROL_UP_NEG, + //DIR_CONTROL_FLAG_DOWN_NUDGE = AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_UP_NEG + return flags; } -- cgit v1.1 From aecaa5106394ea55b2442da74b72094f934a491c Mon Sep 17 00:00:00 2001 From: John Hurliman Date: Thu, 29 Oct 2009 16:31:48 -0700 Subject: * Fixed a NullReferenceException in GetMovementAnimation() and added more protection against NREs in AddNewMovement() * Removed the three second limit on ImprovedTerseObjectUpdate. With the latest fixes I don't think this is necessary, and it generates a lot of unnecessary updates in a crowded sim --- OpenSim/Region/Framework/Scenes/ScenePresence.cs | 64 +++++++++++++----------- 1 file changed, 35 insertions(+), 29 deletions(-) (limited to 'OpenSim/Region/Framework/Scenes/ScenePresence.cs') diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index 04c22d0..9730cd5 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -98,7 +98,7 @@ namespace OpenSim.Region.Framework.Scenes private Vector3 m_lastPosition; private Quaternion m_lastRotation; private Vector3 m_lastVelocity; - private int m_lastTerseSent; + //private int m_lastTerseSent; private bool m_updateflag; private byte m_movementflag; @@ -1120,7 +1120,7 @@ namespace OpenSim.Region.Framework.Scenes else { if (!m_pos.ApproxEquals(m_lastPosition, POSITION_TOLERANCE) || - !m_velocity.ApproxEquals(m_lastVelocity, VELOCITY_TOLERANCE) || + !Velocity.ApproxEquals(m_lastVelocity, VELOCITY_TOLERANCE) || !m_bodyRot.ApproxEquals(m_lastRotation, ROTATION_TOLERANCE)) { if (CameraConstraintActive) @@ -2110,8 +2110,9 @@ namespace OpenSim.Region.Framework.Scenes if (actor == null || !actor.IsColliding) { float fallElapsed = (float)(Environment.TickCount - m_animTickFall) / 1000f; + float fallVelocity = (actor != null) ? actor.Velocity.Z : 0.0f; - if (m_animTickFall == 0 || (fallElapsed > FALL_DELAY && actor.Velocity.Z >= 0.0f)) + if (m_animTickFall == 0 || (fallElapsed > FALL_DELAY && fallVelocity >= 0.0f)) { // Just started falling m_animTickFall = Environment.TickCount; @@ -2262,28 +2263,30 @@ namespace OpenSim.Region.Framework.Scenes direc.Normalize(); direc *= 0.03f * 128f * m_speedModifier; - if (m_physicsActor.Flying) - { - direc *= 4.0f; - //bool controlland = (((m_AgentControlFlags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_UP_NEG) != 0) || ((m_AgentControlFlags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_UP_NEG) != 0)); - //bool colliding = (m_physicsActor.IsColliding==true); - //if (controlland) - // m_log.Info("[AGENT]: landCommand"); - //if (colliding) - // m_log.Info("[AGENT]: colliding"); - //if (m_physicsActor.Flying && colliding && controlland) - //{ - // StopFlying(); - // m_log.Info("[AGENT]: Stop FLying"); - //} - } - else - { - if (!m_physicsActor.Flying && m_physicsActor.IsColliding) + + PhysicsActor actor = m_physicsActor; + if (actor != null) + { + if (actor.Flying) + { + direc *= 4.0f; + //bool controlland = (((m_AgentControlFlags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_UP_NEG) != 0) || ((m_AgentControlFlags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_UP_NEG) != 0)); + //bool colliding = (m_physicsActor.IsColliding==true); + //if (controlland) + // m_log.Info("[AGENT]: landCommand"); + //if (colliding) + // m_log.Info("[AGENT]: colliding"); + //if (m_physicsActor.Flying && colliding && controlland) + //{ + // StopFlying(); + // m_log.Info("[AGENT]: Stop FLying"); + //} + } + else if (!actor.Flying && actor.IsColliding) { if (direc.Z > 2.0f) { - direc.Z *= 3; + direc.Z *= 3.0f; // TODO: PreJump and jump happen too quickly. Many times prejump gets ignored. TrySetMovementAnimation("PREJUMP"); @@ -2307,7 +2310,7 @@ namespace OpenSim.Region.Framework.Scenes const float ROTATION_TOLERANCE = 0.01f; const float VELOCITY_TOLERANCE = 0.001f; const float POSITION_TOLERANCE = 0.05f; - const int TIME_MS_TOLERANCE = 3000; + //const int TIME_MS_TOLERANCE = 3000; SendPrimUpdates(); @@ -2320,21 +2323,24 @@ namespace OpenSim.Region.Framework.Scenes if (m_isChildAgent == false) { PhysicsActor actor = m_physicsActor; - Vector3 velocity = (actor != null) ? actor.Velocity : Vector3.Zero; + + // NOTE: Velocity is not the same as m_velocity. Velocity will attempt to + // grab the latest PhysicsActor velocity, whereas m_velocity is often + // storing a requested force instead of an actual traveling velocity // Throw away duplicate or insignificant updates if (!m_bodyRot.ApproxEquals(m_lastRotation, ROTATION_TOLERANCE) || - !velocity.ApproxEquals(m_lastVelocity, VELOCITY_TOLERANCE) || - !m_pos.ApproxEquals(m_lastPosition, POSITION_TOLERANCE) || - Environment.TickCount - m_lastTerseSent > TIME_MS_TOLERANCE) + !Velocity.ApproxEquals(m_lastVelocity, VELOCITY_TOLERANCE) || + !m_pos.ApproxEquals(m_lastPosition, POSITION_TOLERANCE)) + //Environment.TickCount - m_lastTerseSent > TIME_MS_TOLERANCE) { SendTerseUpdateToAllClients(); // Update the "last" values m_lastPosition = m_pos; m_lastRotation = m_bodyRot; - m_lastVelocity = velocity; - m_lastTerseSent = Environment.TickCount; + m_lastVelocity = Velocity; + //m_lastTerseSent = Environment.TickCount; } // followed suggestion from mic bowman. reversed the two lines below. -- cgit v1.1 From 8a73dc0f8a3a8606439b6f7217d2d14c22bfd43e Mon Sep 17 00:00:00 2001 From: John Hurliman Date: Fri, 30 Oct 2009 03:01:15 -0700 Subject: * Fix for a potential race condition in ScenePresence.AbsolutePosition * Unified the way region handles are stored and used in ScenePresence * Fixed camera position for child agents * CheckForSignificantMovement now checks avatar and camera position (both are important for scene prioritization) * Removing debug code from the previous commit --- OpenSim/Region/Framework/Scenes/ScenePresence.cs | 78 ++++++++++++------------ 1 file changed, 40 insertions(+), 38 deletions(-) (limited to 'OpenSim/Region/Framework/Scenes/ScenePresence.cs') diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs index 9730cd5..6c0d9f2 100644 --- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs +++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs @@ -79,6 +79,15 @@ namespace OpenSim.Region.Framework.Scenes private static readonly byte[] DEFAULT_TEXTURE = AvatarAppearance.GetDefaultTexture().GetBytes(); private static readonly Array DIR_CONTROL_FLAGS = Enum.GetValues(typeof(Dir_ControlFlags)); private static readonly Vector3 HEAD_ADJUSTMENT = new Vector3(0f, 0f, 0.3f); + /// + /// Experimentally determined "fudge factor" to make sit-target positions + /// the same as in SecondLife. Fudge factor was tested for 36 different + /// test cases including prims of type box, sphere, cylinder, and torus, + /// with varying parameters for sit target location, prim size, prim + /// rotation, prim cut, prim twist, prim taper, and prim shear. See mantis + /// issue #1716 + /// + private static readonly Vector3 SIT_TARGET_ADJUSTMENT = new Vector3(0.1f, 0.0f, 0.3f); public UUID currentParcelUUID = UUID.Zero; @@ -115,18 +124,12 @@ namespace OpenSim.Region.Framework.Scenes private float m_sitAvatarHeight = 2.0f; - // experimentally determined "fudge factor" to make sit-target positions - // the same as in SecondLife. Fudge factor was tested for 36 different - // test cases including prims of type box, sphere, cylinder, and torus, - // with varying parameters for sit target location, prim size, prim - // rotation, prim cut, prim twist, prim taper, and prim shear. See mantis - // issue #1716 - private static readonly Vector3 m_sitTargetCorrectionOffset = new Vector3(0.1f, 0.0f, 0.3f); private float m_godlevel; private bool m_invulnerable = true; - private Vector3 m_LastChildAgentUpdatePosition; + private Vector3 m_lastChildAgentUpdatePosition; + private Vector3 m_lastChildAgentUpdateCamPosition; private int m_perfMonMS; @@ -271,11 +274,9 @@ namespace OpenSim.Region.Framework.Scenes get { return m_godlevel; } } - private readonly ulong m_regionHandle; - public ulong RegionHandle { - get { return m_regionHandle; } + get { return m_rootRegionHandle; } } public Vector3 CameraPosition @@ -414,31 +415,27 @@ namespace OpenSim.Region.Framework.Scenes } /// - /// Absolute position of this avatar in 'region cordinates' + /// Position of this avatar relative to the region the avatar is in /// public override Vector3 AbsolutePosition { get { - if (m_physicsActor != null) - { - m_pos.X = m_physicsActor.Position.X; - m_pos.Y = m_physicsActor.Position.Y; - m_pos.Z = m_physicsActor.Position.Z; - } + PhysicsActor actor = m_physicsActor; + if (actor != null) + m_pos = actor.Position; return m_parentPosition + m_pos; } set { - if (m_physicsActor != null) + PhysicsActor actor = m_physicsActor; + if (actor != null) { try { lock (m_scene.SyncRoot) - { m_physicsActor.Position = value; - } } catch (Exception e) { @@ -466,8 +463,6 @@ namespace OpenSim.Region.Framework.Scenes } set { - //m_log.DebugFormat("In {0} setting velocity of {1} to {2}", m_scene.RegionInfo.RegionName, Name, value); - PhysicsActor actor = m_physicsActor; if (actor != null) { @@ -626,7 +621,7 @@ namespace OpenSim.Region.Framework.Scenes { m_sendCourseLocationsMethod = SendCoarseLocationsDefault; CreateSceneViewer(); - m_regionHandle = reginfo.RegionHandle; + m_rootRegionHandle = reginfo.RegionHandle; m_controllingClient = client; m_firstname = m_controllingClient.FirstName; m_lastname = m_controllingClient.LastName; @@ -780,6 +775,8 @@ namespace OpenSim.Region.Framework.Scenes if (gm != null) m_grouptitle = gm.GetGroupTitle(m_uuid); + m_rootRegionHandle = m_scene.RegionInfo.RegionHandle; + m_scene.SetRootAgentScene(m_uuid); // Moved this from SendInitialData to ensure that m_appearance is initialized @@ -810,7 +807,6 @@ namespace OpenSim.Region.Framework.Scenes pos = emergencyPos; } - float localAVHeight = 1.56f; if (m_avHeight != 127.0f) { @@ -905,6 +901,8 @@ namespace OpenSim.Region.Framework.Scenes m_isChildAgent = true; m_scene.SwapRootAgentCount(true); RemoveFromPhysicalScene(); + + // FIXME: Set m_rootRegionHandle to the region handle of the scene this agent is moving into m_scene.EventManager.TriggerOnMakeChildAgent(this); } @@ -1823,7 +1821,7 @@ namespace OpenSim.Region.Framework.Scenes //Quaternion result = (sitTargetOrient * vq) * nq; m_pos = new Vector3(sitTargetPos.X, sitTargetPos.Y, sitTargetPos.Z); - m_pos += m_sitTargetCorrectionOffset; + m_pos += SIT_TARGET_ADJUSTMENT; m_bodyRot = sitTargetOrient; //Rotation = sitTargetOrient; m_parentPosition = part.AbsolutePosition; @@ -2374,7 +2372,7 @@ namespace OpenSim.Region.Framework.Scenes //m_log.DebugFormat("[SCENEPRESENCE]: TerseUpdate: Pos={0} Rot={1} Vel={2}", m_pos, m_bodyRot, m_velocity); - remoteClient.SendAvatarTerseUpdate(new SendAvatarTerseData(m_regionHandle, (ushort)(m_scene.TimeDilation * ushort.MaxValue), LocalId, + remoteClient.SendAvatarTerseUpdate(new SendAvatarTerseData(m_rootRegionHandle, (ushort)(m_scene.TimeDilation * ushort.MaxValue), LocalId, pos, velocity, Vector3.Zero, m_bodyRot, CollisionPlane, m_uuid, null, GetUpdatePriority(remoteClient))); m_scene.StatsReporter.AddAgentTime(Environment.TickCount - m_perfMonMS); @@ -2739,7 +2737,8 @@ namespace OpenSim.Region.Framework.Scenes } // Minimum Draw distance is 64 meters, the Radius of the draw distance sphere is 32m - if (Util.GetDistanceTo(AbsolutePosition, m_LastChildAgentUpdatePosition) >= Scene.ChildReprioritizationDistance) + if (Util.GetDistanceTo(AbsolutePosition, m_lastChildAgentUpdatePosition) >= Scene.ChildReprioritizationDistance || + Util.GetDistanceTo(CameraPosition, m_lastChildAgentUpdateCamPosition) >= Scene.ChildReprioritizationDistance) { ChildAgentDataUpdate cadu = new ChildAgentDataUpdate(); cadu.ActiveGroupID = UUID.Zero.Guid; @@ -2753,7 +2752,7 @@ namespace OpenSim.Region.Framework.Scenes cadu.godlevel = m_godlevel; cadu.GroupAccess = 0; cadu.Position = new sLLVector3(AbsolutePosition); - cadu.regionHandle = m_scene.RegionInfo.RegionHandle; + cadu.regionHandle = m_rootRegionHandle; float multiplier = 1; int innacurateNeighbors = m_scene.GetInaccurateNeighborCount(); if (innacurateNeighbors != 0) @@ -2774,7 +2773,8 @@ namespace OpenSim.Region.Framework.Scenes m_scene.SendOutChildAgentUpdates(agentpos, this); - m_LastChildAgentUpdatePosition = AbsolutePosition; + m_lastChildAgentUpdatePosition = AbsolutePosition; + m_lastChildAgentUpdateCamPosition = CameraPosition; } } @@ -3027,9 +3027,11 @@ namespace OpenSim.Region.Framework.Scenes int shiftx = ((int)rRegionX - (int)tRegionX) * (int)Constants.RegionSize; int shifty = ((int)rRegionY - (int)tRegionY) * (int)Constants.RegionSize; + Vector3 offset = new Vector3(shiftx, shifty, 0f); + m_DrawDistance = cAgentData.Far; - if (cAgentData.Position != new Vector3(-1, -1, -1)) // UGH!! - m_pos = new Vector3(cAgentData.Position.X + shiftx, cAgentData.Position.Y + shifty, cAgentData.Position.Z); + if (cAgentData.Position != new Vector3(-1f, -1f, -1f)) // UGH!! + m_pos = cAgentData.Position + offset; if (Vector3.Distance(AbsolutePosition, posLastSignificantMove) >= Scene.ChildReprioritizationDistance) { @@ -3037,8 +3039,7 @@ namespace OpenSim.Region.Framework.Scenes ReprioritizeUpdates(); } - // It's hard to say here.. We can't really tell where the camera position is unless it's in world cordinates from the sending region - m_CameraCenter = cAgentData.Center; + m_CameraCenter = cAgentData.Center + offset; m_avHeight = cAgentData.Size.Z; //SetHeight(cAgentData.AVHeight); @@ -3051,16 +3052,16 @@ namespace OpenSim.Region.Framework.Scenes m_sceneViewer.Reset(); //cAgentData.AVHeight; - //cAgentData.regionHandle; + m_rootRegionHandle = cAgentData.RegionHandle; //m_velocity = cAgentData.Velocity; } public void CopyTo(AgentData cAgent) { cAgent.AgentID = UUID; - cAgent.RegionHandle = m_scene.RegionInfo.RegionHandle; + cAgent.RegionHandle = m_rootRegionHandle; - cAgent.Position = m_pos; + cAgent.Position = AbsolutePosition; cAgent.Velocity = m_velocity; cAgent.Center = m_CameraCenter; // Don't copy the size; it is inferred from apearance parameters @@ -3157,7 +3158,8 @@ namespace OpenSim.Region.Framework.Scenes public void CopyFrom(AgentData cAgent) { - m_rootRegionHandle= cAgent.RegionHandle; + m_rootRegionHandle = cAgent.RegionHandle; + m_callbackURI = cAgent.CallbackURI; m_pos = cAgent.Position; -- cgit v1.1