aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/Framework/Scenes/ScenePresence.cs
diff options
context:
space:
mode:
Diffstat (limited to 'OpenSim/Region/Framework/Scenes/ScenePresence.cs')
-rw-r--r--OpenSim/Region/Framework/Scenes/ScenePresence.cs1073
1 files changed, 882 insertions, 191 deletions
diff --git a/OpenSim/Region/Framework/Scenes/ScenePresence.cs b/OpenSim/Region/Framework/Scenes/ScenePresence.cs
index 83b761c..d2f84e3 100644
--- a/OpenSim/Region/Framework/Scenes/ScenePresence.cs
+++ b/OpenSim/Region/Framework/Scenes/ScenePresence.cs
@@ -26,6 +26,7 @@
26 */ 26 */
27 27
28using System; 28using System;
29using System.Xml;
29using System.Collections.Generic; 30using System.Collections.Generic;
30using System.Reflection; 31using System.Reflection;
31using System.Timers; 32using System.Timers;
@@ -72,7 +73,7 @@ namespace OpenSim.Region.Framework.Scenes
72// { 73// {
73// m_log.Debug("[ScenePresence] Destructor called"); 74// m_log.Debug("[ScenePresence] Destructor called");
74// } 75// }
75 76
76 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType); 77 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
77 78
78// private static readonly byte[] DEFAULT_TEXTURE = AvatarAppearance.GetDefaultTexture().GetBytes(); 79// private static readonly byte[] DEFAULT_TEXTURE = AvatarAppearance.GetDefaultTexture().GetBytes();
@@ -87,7 +88,9 @@ namespace OpenSim.Region.Framework.Scenes
87 /// rotation, prim cut, prim twist, prim taper, and prim shear. See mantis 88 /// rotation, prim cut, prim twist, prim taper, and prim shear. See mantis
88 /// issue #1716 89 /// issue #1716
89 /// </summary> 90 /// </summary>
90 private static readonly Vector3 SIT_TARGET_ADJUSTMENT = new Vector3(0.1f, 0.0f, 0.3f); 91// private static readonly Vector3 SIT_TARGET_ADJUSTMENT = new Vector3(0.1f, 0.0f, 0.3f);
92 // Value revised by KF 091121 by comparison with SL.
93 private static readonly Vector3 SIT_TARGET_ADJUSTMENT = new Vector3(0.0f, 0.0f, 0.418f);
91 94
92 public UUID currentParcelUUID = UUID.Zero; 95 public UUID currentParcelUUID = UUID.Zero;
93 96
@@ -110,6 +113,7 @@ namespace OpenSim.Region.Framework.Scenes
110 { 113 {
111 get { return m_attachments; } 114 get { return m_attachments; }
112 } 115 }
116
113 protected List<SceneObjectGroup> m_attachments = new List<SceneObjectGroup>(); 117 protected List<SceneObjectGroup> m_attachments = new List<SceneObjectGroup>();
114 118
115 private Dictionary<UUID, ScriptControllers> scriptedcontrols = new Dictionary<UUID, ScriptControllers>(); 119 private Dictionary<UUID, ScriptControllers> scriptedcontrols = new Dictionary<UUID, ScriptControllers>();
@@ -119,10 +123,12 @@ namespace OpenSim.Region.Framework.Scenes
119 private SceneObjectGroup proxyObjectGroup; 123 private SceneObjectGroup proxyObjectGroup;
120 //private SceneObjectPart proxyObjectPart = null; 124 //private SceneObjectPart proxyObjectPart = null;
121 public Vector3 lastKnownAllowedPosition; 125 public Vector3 lastKnownAllowedPosition;
122 public bool sentMessageAboutRestrictedParcelFlyingDown;
123 public Vector4 CollisionPlane = Vector4.UnitW; 126 public Vector4 CollisionPlane = Vector4.UnitW;
124 127
128 private Vector3 m_avInitialPos; // used to calculate unscripted sit rotation
129 private Vector3 m_avUnscriptedSitPos; // for non-scripted prims
125 private Vector3 m_lastPosition; 130 private Vector3 m_lastPosition;
131 private Vector3 m_lastWorldPosition;
126 private Quaternion m_lastRotation; 132 private Quaternion m_lastRotation;
127 private Vector3 m_lastVelocity; 133 private Vector3 m_lastVelocity;
128 //private int m_lastTerseSent; 134 //private int m_lastTerseSent;
@@ -130,6 +136,11 @@ namespace OpenSim.Region.Framework.Scenes
130 private bool m_updateflag; 136 private bool m_updateflag;
131 private byte m_movementflag; 137 private byte m_movementflag;
132 private Vector3? m_forceToApply; 138 private Vector3? m_forceToApply;
139 private int m_userFlags;
140 public int UserFlags
141 {
142 get { return m_userFlags; }
143 }
133 private TeleportFlags m_teleportFlags; 144 private TeleportFlags m_teleportFlags;
134 public TeleportFlags TeleportFlags 145 public TeleportFlags TeleportFlags
135 { 146 {
@@ -160,9 +171,10 @@ namespace OpenSim.Region.Framework.Scenes
160 private int m_perfMonMS; 171 private int m_perfMonMS;
161 172
162 private bool m_setAlwaysRun; 173 private bool m_setAlwaysRun;
163
164 private bool m_forceFly; 174 private bool m_forceFly;
165 private bool m_flyDisabled; 175 private bool m_flyDisabled;
176 private bool m_flyingOld; // add for fly velocity control
177 public bool m_wasFlying; // add for fly velocity control
166 178
167 private float m_speedModifier = 1.0f; 179 private float m_speedModifier = 1.0f;
168 180
@@ -181,7 +193,8 @@ namespace OpenSim.Region.Framework.Scenes
181 protected RegionInfo m_regionInfo; 193 protected RegionInfo m_regionInfo;
182 protected ulong crossingFromRegion; 194 protected ulong crossingFromRegion;
183 195
184 private readonly Vector3[] Dir_Vectors = new Vector3[9]; 196 private readonly Vector3[] Dir_Vectors = new Vector3[11];
197 private bool m_isNudging = false;
185 198
186 // Position of agent's camera in world (region cordinates) 199 // Position of agent's camera in world (region cordinates)
187 protected Vector3 m_CameraCenter; 200 protected Vector3 m_CameraCenter;
@@ -206,17 +219,25 @@ namespace OpenSim.Region.Framework.Scenes
206 private bool m_autopilotMoving; 219 private bool m_autopilotMoving;
207 private Vector3 m_autoPilotTarget; 220 private Vector3 m_autoPilotTarget;
208 private bool m_sitAtAutoTarget; 221 private bool m_sitAtAutoTarget;
222 private Vector3 m_initialSitTarget = Vector3.Zero; //KF: First estimate of where to sit
209 223
210 private string m_nextSitAnimation = String.Empty; 224 private string m_nextSitAnimation = String.Empty;
211 225
212 //PauPaw:Proper PID Controler for autopilot************ 226 //PauPaw:Proper PID Controler for autopilot************
213 private bool m_moveToPositionInProgress; 227 private bool m_moveToPositionInProgress;
214 private Vector3 m_moveToPositionTarget; 228 private Vector3 m_moveToPositionTarget;
229 private Quaternion m_offsetRotation = new Quaternion(0.0f, 0.0f, 0.0f, 1.0f);
215 230
216 private bool m_followCamAuto; 231 private bool m_followCamAuto;
217 232
218 private int m_movementUpdateCount; 233 private int m_movementUpdateCount;
234 private int m_lastColCount = -1; //KF: Look for Collision chnages
235 private int m_updateCount = 0; //KF: Update Anims for a while
236 private static readonly int UPDATE_COUNT = 10; // how many frames to update for
219 private const int NumMovementsBetweenRayCast = 5; 237 private const int NumMovementsBetweenRayCast = 5;
238 private List<uint> m_lastColliders = new List<uint>();
239
240 private object m_syncRoot = new Object();
220 241
221 private bool CameraConstraintActive; 242 private bool CameraConstraintActive;
222 //private int m_moveToPositionStateStatus; 243 //private int m_moveToPositionStateStatus;
@@ -253,7 +274,9 @@ namespace OpenSim.Region.Framework.Scenes
253 DIR_CONTROL_FLAG_UP = AgentManager.ControlFlags.AGENT_CONTROL_UP_POS, 274 DIR_CONTROL_FLAG_UP = AgentManager.ControlFlags.AGENT_CONTROL_UP_POS,
254 DIR_CONTROL_FLAG_DOWN = AgentManager.ControlFlags.AGENT_CONTROL_UP_NEG, 275 DIR_CONTROL_FLAG_DOWN = AgentManager.ControlFlags.AGENT_CONTROL_UP_NEG,
255 DIR_CONTROL_FLAG_FORWARD_NUDGE = AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_AT_POS, 276 DIR_CONTROL_FLAG_FORWARD_NUDGE = AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_AT_POS,
256 DIR_CONTROL_FLAG_BACKWARD_NUDGE = AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_AT_NEG, 277 DIR_CONTROL_FLAG_BACK_NUDGE = AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_AT_NEG,
278 DIR_CONTROL_FLAG_LEFT_NUDGE = AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_LEFT_POS,
279 DIR_CONTROL_FLAG_RIGHT_NUDGE = AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_LEFT_NEG,
257 DIR_CONTROL_FLAG_DOWN_NUDGE = AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_UP_NEG 280 DIR_CONTROL_FLAG_DOWN_NUDGE = AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_UP_NEG
258 } 281 }
259 282
@@ -460,7 +483,8 @@ namespace OpenSim.Region.Framework.Scenes
460 get 483 get
461 { 484 {
462 PhysicsActor actor = m_physicsActor; 485 PhysicsActor actor = m_physicsActor;
463 if (actor != null) 486// if (actor != null)
487 if ((actor != null) && (m_parentID == 0)) // KF Do NOT update m_pos here if Av is sitting!
464 m_pos = actor.Position; 488 m_pos = actor.Position;
465 else 489 else
466 { 490 {
@@ -482,7 +506,7 @@ namespace OpenSim.Region.Framework.Scenes
482 SceneObjectPart part = m_scene.GetSceneObjectPart(m_parentID); 506 SceneObjectPart part = m_scene.GetSceneObjectPart(m_parentID);
483 if (part != null) 507 if (part != null)
484 { 508 {
485 return m_parentPosition + (m_pos * part.GetWorldRotation()); 509 return part.AbsolutePosition + (m_pos * part.GetWorldRotation());
486 } 510 }
487 else 511 else
488 { 512 {
@@ -509,7 +533,8 @@ namespace OpenSim.Region.Framework.Scenes
509 } 533 }
510 } 534 }
511 535
512 m_pos = value; 536 if (m_parentID == 0) // KF Do NOT update m_pos here if Av is sitting!
537 m_pos = value;
513 m_parentPosition = Vector3.Zero; 538 m_parentPosition = Vector3.Zero;
514 } 539 }
515 } 540 }
@@ -553,10 +578,39 @@ namespace OpenSim.Region.Framework.Scenes
553 } 578 }
554 } 579 }
555 580
581 public Quaternion OffsetRotation
582 {
583 get { return m_offsetRotation; }
584 set { m_offsetRotation = value; }
585 }
586
556 public Quaternion Rotation 587 public Quaternion Rotation
557 { 588 {
558 get { return m_bodyRot; } 589 get {
559 set { m_bodyRot = value; } 590 if (m_parentID != 0)
591 {
592 if (m_offsetRotation != null)
593 {
594 return m_offsetRotation;
595 }
596 else
597 {
598 return new Quaternion(0.0f, 0.0f, 0.0f, 1.0f);
599 }
600
601 }
602 else
603 {
604 return m_bodyRot;
605 }
606 }
607 set {
608 m_bodyRot = value;
609 if (m_parentID != 0)
610 {
611 m_offsetRotation = new Quaternion(0.0f, 0.0f, 0.0f, 1.0f);
612 }
613 }
560 } 614 }
561 615
562 public Quaternion PreviousRotation 616 public Quaternion PreviousRotation
@@ -581,11 +635,21 @@ namespace OpenSim.Region.Framework.Scenes
581 635
582 private uint m_parentID; 636 private uint m_parentID;
583 637
638
639 private UUID m_linkedPrim;
640
584 public uint ParentID 641 public uint ParentID
585 { 642 {
586 get { return m_parentID; } 643 get { return m_parentID; }
587 set { m_parentID = value; } 644 set { m_parentID = value; }
588 } 645 }
646
647 public UUID LinkedPrim
648 {
649 get { return m_linkedPrim; }
650 set { m_linkedPrim = value; }
651 }
652
589 public float Health 653 public float Health
590 { 654 {
591 get { return m_health; } 655 get { return m_health; }
@@ -707,7 +771,7 @@ namespace OpenSim.Region.Framework.Scenes
707 CreateSceneViewer(); 771 CreateSceneViewer();
708 m_animator = new ScenePresenceAnimator(this); 772 m_animator = new ScenePresenceAnimator(this);
709 } 773 }
710 774
711 private ScenePresence(IClientAPI client, Scene world, RegionInfo reginfo) : this() 775 private ScenePresence(IClientAPI client, Scene world, RegionInfo reginfo) : this()
712 { 776 {
713 m_DrawDistance = world.DefaultDrawDistance; 777 m_DrawDistance = world.DefaultDrawDistance;
@@ -722,6 +786,7 @@ namespace OpenSim.Region.Framework.Scenes
722 m_localId = m_scene.AllocateLocalId(); 786 m_localId = m_scene.AllocateLocalId();
723 787
724 UserAccount account = m_scene.UserAccountService.GetUserAccount(m_scene.RegionInfo.ScopeID, m_uuid); 788 UserAccount account = m_scene.UserAccountService.GetUserAccount(m_scene.RegionInfo.ScopeID, m_uuid);
789 m_userFlags = account.UserFlags;
725 790
726 if (account != null) 791 if (account != null)
727 m_userLevel = account.UserLevel; 792 m_userLevel = account.UserLevel;
@@ -740,10 +805,7 @@ namespace OpenSim.Region.Framework.Scenes
740 m_reprioritization_timer.AutoReset = false; 805 m_reprioritization_timer.AutoReset = false;
741 806
742 AdjustKnownSeeds(); 807 AdjustKnownSeeds();
743
744 // TODO: I think, this won't send anything, as we are still a child here...
745 Animator.TrySetMovementAnimation("STAND"); 808 Animator.TrySetMovementAnimation("STAND");
746
747 // we created a new ScenePresence (a new child agent) in a fresh region. 809 // we created a new ScenePresence (a new child agent) in a fresh region.
748 // Request info about all the (root) agents in this region 810 // Request info about all the (root) agents in this region
749 // Note: This won't send data *to* other clients in that region (children don't send) 811 // Note: This won't send data *to* other clients in that region (children don't send)
@@ -794,25 +856,47 @@ namespace OpenSim.Region.Framework.Scenes
794 Dir_Vectors[3] = -Vector3.UnitY; //RIGHT 856 Dir_Vectors[3] = -Vector3.UnitY; //RIGHT
795 Dir_Vectors[4] = Vector3.UnitZ; //UP 857 Dir_Vectors[4] = Vector3.UnitZ; //UP
796 Dir_Vectors[5] = -Vector3.UnitZ; //DOWN 858 Dir_Vectors[5] = -Vector3.UnitZ; //DOWN
797 Dir_Vectors[8] = new Vector3(0f, 0f, -0.5f); //DOWN_Nudge 859 Dir_Vectors[6] = new Vector3(0.5f, 0f, 0f); //FORWARD_NUDGE
798 Dir_Vectors[6] = Vector3.UnitX*2; //FORWARD 860 Dir_Vectors[7] = new Vector3(-0.5f, 0f, 0f); //BACK_NUDGE
799 Dir_Vectors[7] = -Vector3.UnitX; //BACK 861 Dir_Vectors[8] = new Vector3(0f, 0.5f, 0f); //LEFT_NUDGE
862 Dir_Vectors[9] = new Vector3(0f, -0.5f, 0f); //RIGHT_NUDGE
863 Dir_Vectors[10] = new Vector3(0f, 0f, -0.5f); //DOWN_Nudge
800 } 864 }
801 865
802 private Vector3[] GetWalkDirectionVectors() 866 private Vector3[] GetWalkDirectionVectors()
803 { 867 {
804 Vector3[] vector = new Vector3[9]; 868 Vector3[] vector = new Vector3[11];
805 vector[0] = new Vector3(m_CameraUpAxis.Z, 0f, -m_CameraAtAxis.Z); //FORWARD 869 vector[0] = new Vector3(m_CameraUpAxis.Z, 0f, -m_CameraAtAxis.Z); //FORWARD
806 vector[1] = new Vector3(-m_CameraUpAxis.Z, 0f, m_CameraAtAxis.Z); //BACK 870 vector[1] = new Vector3(-m_CameraUpAxis.Z, 0f, m_CameraAtAxis.Z); //BACK
807 vector[2] = Vector3.UnitY; //LEFT 871 vector[2] = Vector3.UnitY; //LEFT
808 vector[3] = -Vector3.UnitY; //RIGHT 872 vector[3] = -Vector3.UnitY; //RIGHT
809 vector[4] = new Vector3(m_CameraAtAxis.Z, 0f, m_CameraUpAxis.Z); //UP 873 vector[4] = new Vector3(m_CameraAtAxis.Z, 0f, m_CameraUpAxis.Z); //UP
810 vector[5] = new Vector3(-m_CameraAtAxis.Z, 0f, -m_CameraUpAxis.Z); //DOWN 874 vector[5] = new Vector3(-m_CameraAtAxis.Z, 0f, -m_CameraUpAxis.Z); //DOWN
811 vector[8] = new Vector3(-m_CameraAtAxis.Z, 0f, -m_CameraUpAxis.Z); //DOWN_Nudge 875 vector[6] = new Vector3(m_CameraUpAxis.Z, 0f, -m_CameraAtAxis.Z); //FORWARD_NUDGE
812 vector[6] = (new Vector3(m_CameraUpAxis.Z, 0f, -m_CameraAtAxis.Z) * 2); //FORWARD Nudge 876 vector[7] = new Vector3(-m_CameraUpAxis.Z, 0f, m_CameraAtAxis.Z); //BACK_NUDGE
813 vector[7] = new Vector3(-m_CameraUpAxis.Z, 0f, m_CameraAtAxis.Z); //BACK Nudge 877 vector[8] = Vector3.UnitY; //LEFT_NUDGE
878 vector[9] = -Vector3.UnitY; //RIGHT_NUDGE
879 vector[10] = new Vector3(-m_CameraAtAxis.Z, 0f, -m_CameraUpAxis.Z); //DOWN_NUDGE
814 return vector; 880 return vector;
815 } 881 }
882
883 private bool[] GetDirectionIsNudge()
884 {
885 bool[] isNudge = new bool[11];
886 isNudge[0] = false; //FORWARD
887 isNudge[1] = false; //BACK
888 isNudge[2] = false; //LEFT
889 isNudge[3] = false; //RIGHT
890 isNudge[4] = false; //UP
891 isNudge[5] = false; //DOWN
892 isNudge[6] = true; //FORWARD_NUDGE
893 isNudge[7] = true; //BACK_NUDGE
894 isNudge[8] = true; //LEFT_NUDGE
895 isNudge[9] = true; //RIGHT_NUDGE
896 isNudge[10] = true; //DOWN_Nudge
897 return isNudge;
898 }
899
816 900
817 #endregion 901 #endregion
818 902
@@ -877,6 +961,62 @@ namespace OpenSim.Region.Framework.Scenes
877 pos.Y = crossedBorder.BorderLine.Z - 1; 961 pos.Y = crossedBorder.BorderLine.Z - 1;
878 } 962 }
879 963
964 ILandObject land = m_scene.LandChannel.GetLandObject(pos.X, pos.Y);
965 if (land != null)
966 {
967 // If we come in via login, landmark or map, we want to
968 // honor landing points. If we come in via Lure, we want
969 // to ignore them.
970 if ((m_teleportFlags & (TeleportFlags.ViaLogin | TeleportFlags.ViaRegionID)) == (TeleportFlags.ViaLogin | TeleportFlags.ViaRegionID) ||
971 (m_teleportFlags & TeleportFlags.ViaLandmark) != 0 ||
972 (m_teleportFlags & TeleportFlags.ViaLocation) != 0)
973 {
974 // Don't restrict gods, estate managers, or land owners to
975 // the TP point. This behaviour mimics agni.
976 if (land.LandData.LandingType == (byte)LandingType.LandingPoint &&
977 land.LandData.UserLocation != Vector3.Zero &&
978 GodLevel < 200 &&
979 ((land.LandData.OwnerID != m_uuid &&
980 (!m_scene.Permissions.IsGod(m_uuid)) &&
981 (!m_scene.RegionInfo.EstateSettings.IsEstateManager(m_uuid))) || (m_teleportFlags & TeleportFlags.ViaLocation) != 0))
982 {
983 pos = land.LandData.UserLocation;
984 }
985 }
986
987 land.SendLandUpdateToClient(ControllingClient);
988 }
989
990 if (pos.X < 0 || pos.Y < 0 || pos.Z < 0)
991 {
992 Vector3 emergencyPos = new Vector3(((int)Constants.RegionSize * 0.5f), ((int)Constants.RegionSize * 0.5f), 128);
993
994 if (pos.X < 0)
995 {
996 emergencyPos.X = (int)Constants.RegionSize + pos.X;
997 if (!(pos.Y < 0))
998 emergencyPos.Y = pos.Y;
999 if (!(pos.Z < 0))
1000 emergencyPos.Z = pos.Z;
1001 }
1002 if (pos.Y < 0)
1003 {
1004 emergencyPos.Y = (int)Constants.RegionSize + pos.Y;
1005 if (!(pos.X < 0))
1006 emergencyPos.X = pos.X;
1007 if (!(pos.Z < 0))
1008 emergencyPos.Z = pos.Z;
1009 }
1010 if (pos.Z < 0)
1011 {
1012 emergencyPos.Z = 128;
1013 if (!(pos.Y < 0))
1014 emergencyPos.Y = pos.Y;
1015 if (!(pos.X < 0))
1016 emergencyPos.X = pos.X;
1017 }
1018 }
1019
880 if (pos.X < 0f || pos.Y < 0f || pos.Z < 0f) 1020 if (pos.X < 0f || pos.Y < 0f || pos.Z < 0f)
881 { 1021 {
882 m_log.WarnFormat( 1022 m_log.WarnFormat(
@@ -1022,16 +1162,21 @@ namespace OpenSim.Region.Framework.Scenes
1022 /// <summary> 1162 /// <summary>
1023 /// Removes physics plugin scene representation of this agent if it exists. 1163 /// Removes physics plugin scene representation of this agent if it exists.
1024 /// </summary> 1164 /// </summary>
1025 private void RemoveFromPhysicalScene() 1165 public void RemoveFromPhysicalScene()
1026 { 1166 {
1027 if (PhysicsActor != null) 1167 if (PhysicsActor != null)
1028 { 1168 {
1029 m_physicsActor.OnRequestTerseUpdate -= SendTerseUpdateToAllClients; 1169 try
1030 m_physicsActor.OnOutOfBounds -= OutOfBoundsCall; 1170 {
1031 m_scene.PhysicsScene.RemoveAvatar(PhysicsActor); 1171 m_physicsActor.OnRequestTerseUpdate -= SendTerseUpdateToAllClients;
1032 m_physicsActor.UnSubscribeEvents(); 1172 m_physicsActor.OnOutOfBounds -= OutOfBoundsCall;
1033 m_physicsActor.OnCollisionUpdate -= PhysicsCollisionUpdate; 1173 m_physicsActor.OnCollisionUpdate -= PhysicsCollisionUpdate;
1034 PhysicsActor = null; 1174 m_scene.PhysicsScene.RemoveAvatar(PhysicsActor);
1175 m_physicsActor.UnSubscribeEvents();
1176 PhysicsActor = null;
1177 }
1178 catch
1179 { }
1035 } 1180 }
1036 } 1181 }
1037 1182
@@ -1042,11 +1187,13 @@ namespace OpenSim.Region.Framework.Scenes
1042 public void Teleport(Vector3 pos) 1187 public void Teleport(Vector3 pos)
1043 { 1188 {
1044 bool isFlying = false; 1189 bool isFlying = false;
1190
1045 if (m_physicsActor != null) 1191 if (m_physicsActor != null)
1046 isFlying = m_physicsActor.Flying; 1192 isFlying = m_physicsActor.Flying;
1047 1193
1048 RemoveFromPhysicalScene(); 1194 RemoveFromPhysicalScene();
1049 Velocity = Vector3.Zero; 1195 Velocity = Vector3.Zero;
1196 CheckLandingPoint(ref pos);
1050 AbsolutePosition = pos; 1197 AbsolutePosition = pos;
1051 AddToPhysicalScene(isFlying); 1198 AddToPhysicalScene(isFlying);
1052 if (m_appearance != null) 1199 if (m_appearance != null)
@@ -1056,6 +1203,7 @@ namespace OpenSim.Region.Framework.Scenes
1056 } 1203 }
1057 1204
1058 SendTerseUpdateToAllClients(); 1205 SendTerseUpdateToAllClients();
1206
1059 } 1207 }
1060 1208
1061 public void TeleportWithMomentum(Vector3 pos) 1209 public void TeleportWithMomentum(Vector3 pos)
@@ -1065,6 +1213,7 @@ namespace OpenSim.Region.Framework.Scenes
1065 isFlying = m_physicsActor.Flying; 1213 isFlying = m_physicsActor.Flying;
1066 1214
1067 RemoveFromPhysicalScene(); 1215 RemoveFromPhysicalScene();
1216 CheckLandingPoint(ref pos);
1068 AbsolutePosition = pos; 1217 AbsolutePosition = pos;
1069 AddToPhysicalScene(isFlying); 1218 AddToPhysicalScene(isFlying);
1070 if (m_appearance != null) 1219 if (m_appearance != null)
@@ -1275,6 +1424,7 @@ namespace OpenSim.Region.Framework.Scenes
1275 m_log.Error("[AVATAR]: NonFinite Avatar position detected... Reset Position. Mantis this please. Error #9999902"); 1424 m_log.Error("[AVATAR]: NonFinite Avatar position detected... Reset Position. Mantis this please. Error #9999902");
1276 1425
1277 m_pos = m_LastFinitePos; 1426 m_pos = m_LastFinitePos;
1427
1278 if (!m_pos.IsFinite()) 1428 if (!m_pos.IsFinite())
1279 { 1429 {
1280 m_pos.X = 127f; 1430 m_pos.X = 127f;
@@ -1345,7 +1495,6 @@ namespace OpenSim.Region.Framework.Scenes
1345 m_scene.PhysicsScene.RaycastWorld(m_pos, Vector3.Normalize(m_CameraCenter - posAdjusted), Vector3.Distance(m_CameraCenter, posAdjusted) + 0.3f, RayCastCameraCallback); 1495 m_scene.PhysicsScene.RaycastWorld(m_pos, Vector3.Normalize(m_CameraCenter - posAdjusted), Vector3.Distance(m_CameraCenter, posAdjusted) + 0.3f, RayCastCameraCallback);
1346 } 1496 }
1347 } 1497 }
1348
1349 lock (scriptedcontrols) 1498 lock (scriptedcontrols)
1350 { 1499 {
1351 if (scriptedcontrols.Count > 0) 1500 if (scriptedcontrols.Count > 0)
@@ -1360,6 +1509,9 @@ namespace OpenSim.Region.Framework.Scenes
1360 1509
1361 if ((flags & AgentManager.ControlFlags.AGENT_CONTROL_SIT_ON_GROUND) != 0) 1510 if ((flags & AgentManager.ControlFlags.AGENT_CONTROL_SIT_ON_GROUND) != 0)
1362 { 1511 {
1512 m_updateCount = 0; // Kill animation update burst so that the SIT_G.. will stick.
1513 Animator.TrySetMovementAnimation("SIT_GROUND_CONSTRAINED");
1514
1363 // TODO: This doesn't prevent the user from walking yet. 1515 // TODO: This doesn't prevent the user from walking yet.
1364 // Setting parent ID would fix this, if we knew what value 1516 // Setting parent ID would fix this, if we knew what value
1365 // to use. Or we could add a m_isSitting variable. 1517 // to use. Or we could add a m_isSitting variable.
@@ -1408,12 +1560,20 @@ namespace OpenSim.Region.Framework.Scenes
1408 if (actor.Flying != oldflying) 1560 if (actor.Flying != oldflying)
1409 update_movementflag = true; 1561 update_movementflag = true;
1410 1562
1563 if (m_animator.m_jumping) // add for jumping
1564 update_movementflag = true;
1565
1411 if (q != m_bodyRot) 1566 if (q != m_bodyRot)
1412 { 1567 {
1413 m_bodyRot = q; 1568 m_bodyRot = q;
1414 update_rotation = true; 1569 update_rotation = true;
1415 } 1570 }
1416 1571
1572 //guilty until proven innocent..
1573 bool Nudging = true;
1574 //Basically, if there is at least one non-nudge control then we don't need
1575 //to worry about stopping the avatar
1576
1417 if (m_parentID == 0) 1577 if (m_parentID == 0)
1418 { 1578 {
1419 bool bAllowUpdateMoveToPosition = false; 1579 bool bAllowUpdateMoveToPosition = false;
@@ -1428,9 +1588,12 @@ namespace OpenSim.Region.Framework.Scenes
1428 else 1588 else
1429 dirVectors = Dir_Vectors; 1589 dirVectors = Dir_Vectors;
1430 1590
1431 // The fact that m_movementflag is a byte needs to be fixed 1591 bool[] isNudge = GetDirectionIsNudge();
1432 // it really should be a uint 1592
1433 uint nudgehack = 250; 1593
1594
1595
1596
1434 foreach (Dir_ControlFlags DCF in DIR_CONTROL_FLAGS) 1597 foreach (Dir_ControlFlags DCF in DIR_CONTROL_FLAGS)
1435 { 1598 {
1436 if (((uint)flags & (uint)DCF) != 0) 1599 if (((uint)flags & (uint)DCF) != 0)
@@ -1440,40 +1603,28 @@ namespace OpenSim.Region.Framework.Scenes
1440 try 1603 try
1441 { 1604 {
1442 agent_control_v3 += dirVectors[i]; 1605 agent_control_v3 += dirVectors[i];
1443 //m_log.DebugFormat("[Motion]: {0}, {1}",i, dirVectors[i]); 1606 if (isNudge[i] == false)
1607 {
1608 Nudging = false;
1609 }
1444 } 1610 }
1445 catch (IndexOutOfRangeException) 1611 catch (IndexOutOfRangeException)
1446 { 1612 {
1447 // Why did I get this? 1613 // Why did I get this?
1448 } 1614 }
1449 1615
1450 if ((m_movementflag & (byte)(uint)DCF) == 0) 1616 if ((m_movementflag & (uint)DCF) == 0)
1451 { 1617 {
1452 if (DCF == Dir_ControlFlags.DIR_CONTROL_FLAG_FORWARD_NUDGE || DCF == Dir_ControlFlags.DIR_CONTROL_FLAG_BACKWARD_NUDGE)
1453 {
1454 m_movementflag |= (byte)nudgehack;
1455 }
1456 m_movementflag += (byte)(uint)DCF; 1618 m_movementflag += (byte)(uint)DCF;
1457 update_movementflag = true; 1619 update_movementflag = true;
1458 } 1620 }
1459 } 1621 }
1460 else 1622 else
1461 { 1623 {
1462 if ((m_movementflag & (byte)(uint)DCF) != 0 || 1624 if ((m_movementflag & (uint)DCF) != 0)
1463 ((DCF == Dir_ControlFlags.DIR_CONTROL_FLAG_FORWARD_NUDGE || DCF == Dir_ControlFlags.DIR_CONTROL_FLAG_BACKWARD_NUDGE)
1464 && ((m_movementflag & (byte)nudgehack) == nudgehack))
1465 ) // This or is for Nudge forward
1466 { 1625 {
1467 m_movementflag -= ((byte)(uint)DCF); 1626 m_movementflag -= (byte)(uint)DCF;
1468
1469 update_movementflag = true; 1627 update_movementflag = true;
1470 /*
1471 if ((DCF == Dir_ControlFlags.DIR_CONTROL_FLAG_FORWARD_NUDGE || DCF == Dir_ControlFlags.DIR_CONTROL_FLAG_BACKWARD_NUDGE)
1472 && ((m_movementflag & (byte)nudgehack) == nudgehack))
1473 {
1474 m_log.Debug("Removed Hack flag");
1475 }
1476 */
1477 } 1628 }
1478 else 1629 else
1479 { 1630 {
@@ -1482,7 +1633,6 @@ namespace OpenSim.Region.Framework.Scenes
1482 } 1633 }
1483 i++; 1634 i++;
1484 } 1635 }
1485
1486 //Paupaw:Do Proper PID for Autopilot here 1636 //Paupaw:Do Proper PID for Autopilot here
1487 if (bResetMoveToPosition) 1637 if (bResetMoveToPosition)
1488 { 1638 {
@@ -1494,8 +1644,41 @@ namespace OpenSim.Region.Framework.Scenes
1494 1644
1495 if (bAllowUpdateMoveToPosition && (m_moveToPositionInProgress && !m_autopilotMoving)) 1645 if (bAllowUpdateMoveToPosition && (m_moveToPositionInProgress && !m_autopilotMoving))
1496 { 1646 {
1647/*
1648 bool twoD = false;
1649 bool there = false;
1650 if (Animator != null)
1651 {
1652 switch (Animator.CurrentMovementAnimation)
1653 {
1654 case "STAND":
1655 case "WALK":
1656 case "RUN":
1657 case "CROUCH":
1658 case "CROUCHWALK":
1659 {
1660 twoD = true;
1661 }
1662 break;
1663 }
1664 }
1665
1666 if (twoD)
1667 {
1668*/
1669 Vector3 abspos = new Vector3(AbsolutePosition.X, AbsolutePosition.Y, 0.0f);
1670 Vector3 tgt = new Vector3(m_moveToPositionTarget.X, m_moveToPositionTarget.Y, 0.0f);
1671/* if (Util.GetDistanceTo(abspos, tgt) <= 0.5f) there = true;
1672 }
1673 else
1674 {
1675 if (Util.GetDistanceTo(AbsolutePosition, m_moveToPositionTarget) <= 0.5f) there = true;
1676 }
1677*/
1497 //Check the error term of the current position in relation to the target position 1678 //Check the error term of the current position in relation to the target position
1498 if (Util.GetDistanceTo(AbsolutePosition, m_moveToPositionTarget) <= 0.5f) 1679// if (Util.GetDistanceTo(AbsolutePosition, m_moveToPositionTarget) <= 0.5f)
1680// if (there)
1681 if (Util.GetDistanceTo(abspos, tgt) <= 0.5f)
1499 { 1682 {
1500 // we are close enough to the target 1683 // we are close enough to the target
1501 m_moveToPositionTarget = Vector3.Zero; 1684 m_moveToPositionTarget = Vector3.Zero;
@@ -1512,11 +1695,15 @@ namespace OpenSim.Region.Framework.Scenes
1512 // unknown forces are acting on the avatar and we need to adaptively respond 1695 // unknown forces are acting on the avatar and we need to adaptively respond
1513 // to such forces, but the following simple approach seems to works fine. 1696 // to such forces, but the following simple approach seems to works fine.
1514 Vector3 LocalVectorToTarget3D = 1697 Vector3 LocalVectorToTarget3D =
1515 (m_moveToPositionTarget - AbsolutePosition) // vector from cur. pos to target in global coords 1698// (m_moveToPositionTarget - AbsolutePosition) // vector from cur. pos to target in global coords
1699 (tgt - abspos)
1516 * Matrix4.CreateFromQuaternion(Quaternion.Inverse(bodyRotation)); // change to avatar coords 1700 * Matrix4.CreateFromQuaternion(Quaternion.Inverse(bodyRotation)); // change to avatar coords
1517 // Ignore z component of vector 1701 // Ignore z component of vector
1518 Vector3 LocalVectorToTarget2D = new Vector3((float)(LocalVectorToTarget3D.X), (float)(LocalVectorToTarget3D.Y), 0f); 1702 Vector3 LocalVectorToTarget2D = new Vector3((float)(LocalVectorToTarget3D.X), (float)(LocalVectorToTarget3D.Y), 0f);
1519 LocalVectorToTarget2D.Normalize(); 1703 LocalVectorToTarget2D.Normalize();
1704
1705 //We're not nudging
1706 Nudging = false;
1520 agent_control_v3 += LocalVectorToTarget2D; 1707 agent_control_v3 += LocalVectorToTarget2D;
1521 1708
1522 // update avatar movement flags. the avatar coordinate system is as follows: 1709 // update avatar movement flags. the avatar coordinate system is as follows:
@@ -1607,13 +1794,13 @@ namespace OpenSim.Region.Framework.Scenes
1607 // m_log.DebugFormat( 1794 // m_log.DebugFormat(
1608 // "In {0} adding velocity to {1} of {2}", m_scene.RegionInfo.RegionName, Name, agent_control_v3); 1795 // "In {0} adding velocity to {1} of {2}", m_scene.RegionInfo.RegionName, Name, agent_control_v3);
1609 1796
1610 AddNewMovement(agent_control_v3, q); 1797 AddNewMovement(agent_control_v3, q, Nudging);
1611 1798
1612 1799
1613 } 1800 }
1614 } 1801 }
1615 1802
1616 if (update_movementflag && ((flags & AgentManager.ControlFlags.AGENT_CONTROL_SIT_ON_GROUND) == 0) && (m_parentID == 0) && !SitGround) 1803 if (update_movementflag && !SitGround)
1617 Animator.UpdateMovementAnimations(); 1804 Animator.UpdateMovementAnimations();
1618 1805
1619 m_scene.EventManager.TriggerOnClientMovement(this); 1806 m_scene.EventManager.TriggerOnClientMovement(this);
@@ -1628,7 +1815,6 @@ namespace OpenSim.Region.Framework.Scenes
1628 m_sitAtAutoTarget = false; 1815 m_sitAtAutoTarget = false;
1629 PrimitiveBaseShape proxy = PrimitiveBaseShape.Default; 1816 PrimitiveBaseShape proxy = PrimitiveBaseShape.Default;
1630 //proxy.PCode = (byte)PCode.ParticleSystem; 1817 //proxy.PCode = (byte)PCode.ParticleSystem;
1631
1632 proxyObjectGroup = new SceneObjectGroup(UUID, Pos, Rotation, proxy); 1818 proxyObjectGroup = new SceneObjectGroup(UUID, Pos, Rotation, proxy);
1633 proxyObjectGroup.AttachToScene(m_scene); 1819 proxyObjectGroup.AttachToScene(m_scene);
1634 1820
@@ -1647,8 +1833,15 @@ namespace OpenSim.Region.Framework.Scenes
1647// } 1833// }
1648 } 1834 }
1649 1835
1836 public void StopMoveToPosition()
1837 {
1838 m_moveToPositionTarget = Vector3.Zero;
1839 m_moveToPositionInProgress = false;
1840 }
1841
1650 public void DoMoveToPosition(Object sender, string method, List<String> args) 1842 public void DoMoveToPosition(Object sender, string method, List<String> args)
1651 { 1843 {
1844//Console.WriteLine("SP:DoMoveToPosition");
1652 try 1845 try
1653 { 1846 {
1654 float locx = 0f; 1847 float locx = 0f;
@@ -1670,7 +1863,7 @@ namespace OpenSim.Region.Framework.Scenes
1670 } 1863 }
1671 m_moveToPositionInProgress = true; 1864 m_moveToPositionInProgress = true;
1672 m_moveToPositionTarget = new Vector3(locx, locy, locz); 1865 m_moveToPositionTarget = new Vector3(locx, locy, locz);
1673 } 1866 }
1674 catch (Exception ex) 1867 catch (Exception ex)
1675 { 1868 {
1676 //Why did I get this error? 1869 //Why did I get this error?
@@ -1692,7 +1885,7 @@ namespace OpenSim.Region.Framework.Scenes
1692 Velocity = Vector3.Zero; 1885 Velocity = Vector3.Zero;
1693 SendAvatarDataToAllAgents(); 1886 SendAvatarDataToAllAgents();
1694 1887
1695 //HandleAgentSit(ControllingClient, m_requestedSitTargetUUID); 1888 HandleAgentSit(ControllingClient, m_requestedSitTargetUUID); //KF ??
1696 } 1889 }
1697 //ControllingClient.SendSitResponse(m_requestedSitTargetID, m_requestedSitOffset, Quaternion.Identity, false, Vector3.Zero, Vector3.Zero, false); 1890 //ControllingClient.SendSitResponse(m_requestedSitTargetID, m_requestedSitOffset, Quaternion.Identity, false, Vector3.Zero, Vector3.Zero, false);
1698 m_requestedSitTargetUUID = UUID.Zero; 1891 m_requestedSitTargetUUID = UUID.Zero;
@@ -1729,25 +1922,22 @@ namespace OpenSim.Region.Framework.Scenes
1729 1922
1730 if (m_parentID != 0) 1923 if (m_parentID != 0)
1731 { 1924 {
1732 m_log.Debug("StandupCode Executed"); 1925 SceneObjectPart part = m_scene.GetSceneObjectPart(m_requestedSitTargetID);
1733 SceneObjectPart part = m_scene.GetSceneObjectPart(m_parentID);
1734 if (part != null) 1926 if (part != null)
1735 { 1927 {
1928 part.TaskInventory.LockItemsForRead(true);
1736 TaskInventoryDictionary taskIDict = part.TaskInventory; 1929 TaskInventoryDictionary taskIDict = part.TaskInventory;
1737 if (taskIDict != null) 1930 if (taskIDict != null)
1738 { 1931 {
1739 lock (taskIDict) 1932 foreach (UUID taskID in taskIDict.Keys)
1740 { 1933 {
1741 foreach (UUID taskID in taskIDict.Keys) 1934 UnRegisterControlEventsToScript(LocalId, taskID);
1742 { 1935 taskIDict[taskID].PermsMask &= ~(
1743 UnRegisterControlEventsToScript(LocalId, taskID); 1936 2048 | //PERMISSION_CONTROL_CAMERA
1744 taskIDict[taskID].PermsMask &= ~( 1937 4); // PERMISSION_TAKE_CONTROLS
1745 2048 | //PERMISSION_CONTROL_CAMERA
1746 4); // PERMISSION_TAKE_CONTROLS
1747 }
1748 } 1938 }
1749
1750 } 1939 }
1940 part.TaskInventory.LockItemsForRead(false);
1751 // Reset sit target. 1941 // Reset sit target.
1752 if (part.GetAvatarOnSitTarget() == UUID) 1942 if (part.GetAvatarOnSitTarget() == UUID)
1753 part.SitTargetAvatar = UUID.Zero; 1943 part.SitTargetAvatar = UUID.Zero;
@@ -1756,16 +1946,55 @@ namespace OpenSim.Region.Framework.Scenes
1756 m_parentPosition = part.GetWorldPosition(); 1946 m_parentPosition = part.GetWorldPosition();
1757 ControllingClient.SendClearFollowCamProperties(part.ParentUUID); 1947 ControllingClient.SendClearFollowCamProperties(part.ParentUUID);
1758 } 1948 }
1949 // part.GetWorldRotation() is the rotation of the object being sat on
1950 // Rotation is the sittiing Av's rotation
1951
1952 Quaternion partRot;
1953// if (part.LinkNum == 1)
1954// { // Root prim of linkset
1955// partRot = part.ParentGroup.RootPart.RotationOffset;
1956// }
1957// else
1958// { // single or child prim
1959
1960// }
1961 if (part == null) //CW: Part may be gone. llDie() for example.
1962 {
1963 partRot = new Quaternion(0.0f, 0.0f, 0.0f, 1.0f);
1964 }
1965 else
1966 {
1967 partRot = part.GetWorldRotation();
1968 }
1759 1969
1970 Quaternion partIRot = Quaternion.Inverse(partRot);
1971
1972 Quaternion avatarRot = Quaternion.Inverse(Quaternion.Inverse(Rotation) * partIRot); // world or. of the av
1973 Vector3 avStandUp = new Vector3(0.3f, 0f, 0f) * avatarRot; // 0.3M infront of av
1974
1975
1760 if (m_physicsActor == null) 1976 if (m_physicsActor == null)
1761 { 1977 {
1762 AddToPhysicalScene(false); 1978 AddToPhysicalScene(false);
1763 } 1979 }
1764 1980 //CW: If the part isn't null then we can set the current position
1765 m_pos += m_parentPosition + new Vector3(0.0f, 0.0f, 2.0f*m_sitAvatarHeight); 1981 if (part != null)
1766 m_parentPosition = Vector3.Zero; 1982 {
1767 1983 Vector3 avWorldStandUp = avStandUp + part.GetWorldPosition() + ((m_pos - part.OffsetPosition) * partRot); // + av sit offset!
1768 m_parentID = 0; 1984 AbsolutePosition = avWorldStandUp; //KF: Fix stand up.
1985 part.IsOccupied = false;
1986 part.ParentGroup.DeleteAvatar(ControllingClient.AgentId);
1987 }
1988 else
1989 {
1990 //CW: Since the part doesn't exist, a coarse standup position isn't an issue
1991 AbsolutePosition = m_lastWorldPosition;
1992 }
1993
1994 m_parentPosition = Vector3.Zero;
1995 m_parentID = 0;
1996 m_linkedPrim = UUID.Zero;
1997 m_offsetRotation = new Quaternion(0.0f, 0.0f, 0.0f, 1.0f);
1769 SendAvatarDataToAllAgents(); 1998 SendAvatarDataToAllAgents();
1770 m_requestedSitTargetID = 0; 1999 m_requestedSitTargetID = 0;
1771 if (m_physicsActor != null && m_appearance != null) 2000 if (m_physicsActor != null && m_appearance != null)
@@ -1774,7 +2003,6 @@ namespace OpenSim.Region.Framework.Scenes
1774 SetHeight(m_appearance.AvatarHeight); 2003 SetHeight(m_appearance.AvatarHeight);
1775 } 2004 }
1776 } 2005 }
1777
1778 Animator.TrySetMovementAnimation("STAND"); 2006 Animator.TrySetMovementAnimation("STAND");
1779 } 2007 }
1780 2008
@@ -1805,13 +2033,9 @@ namespace OpenSim.Region.Framework.Scenes
1805 Vector3 avSitOffSet = part.SitTargetPosition; 2033 Vector3 avSitOffSet = part.SitTargetPosition;
1806 Quaternion avSitOrientation = part.SitTargetOrientation; 2034 Quaternion avSitOrientation = part.SitTargetOrientation;
1807 UUID avOnTargetAlready = part.GetAvatarOnSitTarget(); 2035 UUID avOnTargetAlready = part.GetAvatarOnSitTarget();
1808 2036 bool SitTargetOccupied = (avOnTargetAlready != UUID.Zero);
1809 bool SitTargetUnOccupied = (!(avOnTargetAlready != UUID.Zero)); 2037 bool SitTargetisSet = (Vector3.Zero != avSitOffSet); //NB Latest SL Spec shows Sit Rotation setting is ignored.
1810 bool SitTargetisSet = 2038 if (SitTargetisSet && !SitTargetOccupied)
1811 (!(avSitOffSet.X == 0f && avSitOffSet.Y == 0f && avSitOffSet.Z == 0f && avSitOrientation.W == 1f &&
1812 avSitOrientation.X == 0f && avSitOrientation.Y == 0f && avSitOrientation.Z == 0f));
1813
1814 if (SitTargetisSet && SitTargetUnOccupied)
1815 { 2039 {
1816 //switch the target to this prim 2040 //switch the target to this prim
1817 return part; 2041 return part;
@@ -1825,85 +2049,168 @@ namespace OpenSim.Region.Framework.Scenes
1825 private void SendSitResponse(IClientAPI remoteClient, UUID targetID, Vector3 offset, Quaternion pSitOrientation) 2049 private void SendSitResponse(IClientAPI remoteClient, UUID targetID, Vector3 offset, Quaternion pSitOrientation)
1826 { 2050 {
1827 bool autopilot = true; 2051 bool autopilot = true;
2052 Vector3 autopilotTarget = new Vector3();
2053 Quaternion sitOrientation = Quaternion.Identity;
1828 Vector3 pos = new Vector3(); 2054 Vector3 pos = new Vector3();
1829 Quaternion sitOrientation = pSitOrientation;
1830 Vector3 cameraEyeOffset = Vector3.Zero; 2055 Vector3 cameraEyeOffset = Vector3.Zero;
1831 Vector3 cameraAtOffset = Vector3.Zero; 2056 Vector3 cameraAtOffset = Vector3.Zero;
1832 bool forceMouselook = false; 2057 bool forceMouselook = false;
1833 2058
1834 //SceneObjectPart part = m_scene.GetSceneObjectPart(targetID); 2059 //SceneObjectPart part = m_scene.GetSceneObjectPart(targetID);
1835 SceneObjectPart part = FindNextAvailableSitTarget(targetID); 2060 SceneObjectPart part = FindNextAvailableSitTarget(targetID);
1836 if (part != null) 2061 if (part == null) return;
1837 { 2062
1838 // TODO: determine position to sit at based on scene geometry; don't trust offset from client 2063 // TODO: determine position to sit at based on scene geometry; don't trust offset from client
1839 // see http://wiki.secondlife.com/wiki/User:Andrew_Linden/Office_Hours/2007_11_06 for details on how LL does it 2064 // see http://wiki.secondlife.com/wiki/User:Andrew_Linden/Office_Hours/2007_11_06 for details on how LL does it
1840 2065
1841 // Is a sit target available? 2066 // part is the prim to sit on
1842 Vector3 avSitOffSet = part.SitTargetPosition; 2067 // offset is the world-ref vector distance from that prim center to the click-spot
1843 Quaternion avSitOrientation = part.SitTargetOrientation; 2068 // UUID is the UUID of the Avatar doing the clicking
1844 UUID avOnTargetAlready = part.GetAvatarOnSitTarget(); 2069
1845 2070 m_avInitialPos = AbsolutePosition; // saved to calculate unscripted sit rotation
1846 bool SitTargetUnOccupied = (!(avOnTargetAlready != UUID.Zero)); 2071
1847 bool SitTargetisSet = 2072 // Is a sit target available?
1848 (!(avSitOffSet.X == 0f && avSitOffSet.Y == 0f && avSitOffSet.Z == 0f && 2073 Vector3 avSitOffSet = part.SitTargetPosition;
1849 ( 2074 Quaternion avSitOrientation = part.SitTargetOrientation;
1850 avSitOrientation.X == 0f && avSitOrientation.Y == 0f && avSitOrientation.Z == 0f && avSitOrientation.W == 1f // Valid Zero Rotation quaternion 2075
1851 || avSitOrientation.X == 0f && avSitOrientation.Y == 0f && avSitOrientation.Z == 1f && avSitOrientation.W == 0f // W-Z Mapping was invalid at one point 2076 bool SitTargetisSet = (Vector3.Zero != avSitOffSet); //NB Latest SL Spec shows Sit Rotation setting is ignored.
1852 || avSitOrientation.X == 0f && avSitOrientation.Y == 0f && avSitOrientation.Z == 0f && avSitOrientation.W == 0f // Invalid Quaternion 2077 // Quaternion partIRot = Quaternion.Inverse(part.GetWorldRotation());
1853 ) 2078 Quaternion partRot;
1854 )); 2079// if (part.LinkNum == 1)
1855 2080// { // Root prim of linkset
1856 if (SitTargetisSet && SitTargetUnOccupied) 2081// partRot = part.ParentGroup.RootPart.RotationOffset;
1857 { 2082// }
1858 part.SitTargetAvatar = UUID; 2083// else
1859 offset = new Vector3(avSitOffSet.X, avSitOffSet.Y, avSitOffSet.Z); 2084// { // single or child prim
1860 sitOrientation = avSitOrientation; 2085 partRot = part.GetWorldRotation();
1861 autopilot = false; 2086// }
1862 } 2087 Quaternion partIRot = Quaternion.Inverse(partRot);
1863 part.ParentGroup.TriggerScriptChangedEvent(Changed.LINK); 2088//Console.WriteLine("SendSitResponse offset=" + offset + " Occup=" + part.IsOccupied + " TargSet=" + SitTargetisSet);
1864 2089 // Sit analysis rewritten by KF 091125
1865 pos = part.AbsolutePosition + offset; 2090 if (SitTargetisSet) // scipted sit
1866 //if (Math.Abs(part.AbsolutePosition.Z - AbsolutePosition.Z) > 1) 2091 {
1867 //{ 2092 if (!part.IsOccupied)
1868 // offset = pos; 2093 {
1869 //autopilot = false; 2094//Console.WriteLine("Scripted, unoccupied");
1870 //} 2095 part.SitTargetAvatar = UUID; // set that Av will be on it
1871 if (m_physicsActor != null) 2096 offset = new Vector3(avSitOffSet.X, avSitOffSet.Y, avSitOffSet.Z); // change ofset to the scripted one
1872 { 2097
1873 // If we're not using the client autopilot, we're immediately warping the avatar to the location 2098 Quaternion nrot = avSitOrientation;
1874 // We can remove the physicsActor until they stand up. 2099 if (!part.IsRoot)
1875 m_sitAvatarHeight = m_physicsActor.Size.Z;
1876
1877 if (autopilot)
1878 { 2100 {
1879 if (Util.GetDistanceTo(AbsolutePosition, pos) < 4.5) 2101 nrot = part.RotationOffset * avSitOrientation;
1880 {
1881 autopilot = false;
1882
1883 RemoveFromPhysicalScene();
1884 AbsolutePosition = pos + new Vector3(0.0f, 0.0f, m_sitAvatarHeight);
1885 }
1886 } 2102 }
1887 else 2103 sitOrientation = nrot; // Change rotatione to the scripted one
2104 OffsetRotation = nrot;
2105 autopilot = false; // Jump direct to scripted llSitPos()
2106 }
2107 else
2108 {
2109//Console.WriteLine("Scripted, occupied");
2110 return;
2111 }
2112 }
2113 else // Not Scripted
2114 {
2115 if ( (Math.Abs(offset.X) > 0.1f) || (Math.Abs(offset.Y) > 0.1f) ) // Changed 0.5M to 0.1M as they want to be able to sit close together
2116 {
2117 // large prim & offset, ignore if other Avs sitting
2118// offset.Z -= 0.05f;
2119 m_avUnscriptedSitPos = offset * partIRot; // (non-zero) sit where clicked
2120 autopilotTarget = part.AbsolutePosition + offset; // World location of clicked point
2121
2122//Console.WriteLine(" offset ={0}", offset);
2123//Console.WriteLine(" UnscriptedSitPos={0}", m_avUnscriptedSitPos);
2124//Console.WriteLine(" autopilotTarget={0}", autopilotTarget);
2125
2126 }
2127 else // small offset
2128 {
2129//Console.WriteLine("Small offset");
2130 if (!part.IsOccupied)
2131 {
2132 m_avUnscriptedSitPos = Vector3.Zero; // Zero = Sit on prim center
2133 autopilotTarget = part.AbsolutePosition;
2134//Console.WriteLine("UsSmall autopilotTarget={0}", autopilotTarget);
2135 }
2136 else return; // occupied small
2137 } // end large/small
2138 } // end Scripted/not
2139
2140 part.ParentGroup.TriggerScriptChangedEvent(Changed.LINK);
2141
2142 cameraAtOffset = part.GetCameraAtOffset();
2143 cameraEyeOffset = part.GetCameraEyeOffset();
2144 forceMouselook = part.GetForceMouselook();
2145 if(cameraAtOffset == Vector3.Zero) cameraAtOffset = new Vector3(0f, 0f, 0.1f); //
2146 if(cameraEyeOffset == Vector3.Zero) cameraEyeOffset = new Vector3(0f, 0f, 0.1f); //
2147
2148 if (m_physicsActor != null)
2149 {
2150 // If we're not using the client autopilot, we're immediately warping the avatar to the location
2151 // We can remove the physicsActor until they stand up.
2152 m_sitAvatarHeight = m_physicsActor.Size.Z;
2153 if (autopilot)
2154 { // its not a scripted sit
2155// if (Util.GetDistanceTo(AbsolutePosition, autopilotTarget) < 4.5)
2156 if( (Math.Abs(AbsolutePosition.X - autopilotTarget.X) < 256.0f) && (Math.Abs(AbsolutePosition.Y - autopilotTarget.Y) < 256.0f) )
1888 { 2157 {
2158 autopilot = false; // close enough
2159 m_lastWorldPosition = m_pos; /* CW - This give us a position to return the avatar to if the part is killed before standup.
2160 Not using the part's position because returning the AV to the last known standing
2161 position is likely to be more friendly, isn't it? */
1889 RemoveFromPhysicalScene(); 2162 RemoveFromPhysicalScene();
1890 } 2163 Velocity = Vector3.Zero;
2164 AbsolutePosition = autopilotTarget + new Vector3(0.0f, 0.0f, (m_sitAvatarHeight / 2.0f)); // Warp av to over sit target
2165 } // else the autopilot will get us close
2166 }
2167 else
2168 { // its a scripted sit
2169 m_lastWorldPosition = part.AbsolutePosition; /* CW - This give us a position to return the avatar to if the part is killed before standup.
2170 I *am* using the part's position this time because we have no real idea how far away
2171 the avatar is from the sit target. */
2172 RemoveFromPhysicalScene();
2173 Velocity = Vector3.Zero;
1891 } 2174 }
1892
1893 cameraAtOffset = part.GetCameraAtOffset();
1894 cameraEyeOffset = part.GetCameraEyeOffset();
1895 forceMouselook = part.GetForceMouselook();
1896 } 2175 }
1897 2176 else return; // physactor is null!
1898 ControllingClient.SendSitResponse(targetID, offset, sitOrientation, autopilot, cameraAtOffset, cameraEyeOffset, forceMouselook); 2177
1899 m_requestedSitTargetUUID = targetID; 2178 Vector3 offsetr; // = offset * partIRot;
2179 // KF: In a linkset, offsetr needs to be relative to the group root! 091208
2180 // offsetr = (part.OffsetPosition * Quaternion.Inverse(part.ParentGroup.RootPart.RotationOffset)) + (offset * partIRot);
2181 // if (part.LinkNum < 2) 091216 All this was necessary because of the GetWorldRotation error.
2182 // { // Single, or Root prim of linkset, target is ClickOffset * RootRot
2183 //offsetr = offset * partIRot;
2184//
2185 // }
2186 // else
2187 // { // Child prim, offset is (ChildOffset * RootRot) + (ClickOffset * ChildRot)
2188 // offsetr = //(part.OffsetPosition * Quaternion.Inverse(part.ParentGroup.RootPart.RotationOffset)) +
2189 // (offset * partRot);
2190 // }
2191
2192//Console.WriteLine(" ");
2193//Console.WriteLine("link number ={0}", part.LinkNum);
2194//Console.WriteLine("Prim offset ={0}", part.OffsetPosition );
2195//Console.WriteLine("Root Rotate ={0}", part.ParentGroup.RootPart.RotationOffset);
2196//Console.WriteLine("Click offst ={0}", offset);
2197//Console.WriteLine("Prim Rotate ={0}", part.GetWorldRotation());
2198//Console.WriteLine("offsetr ={0}", offsetr);
2199//Console.WriteLine("Camera At ={0}", cameraAtOffset);
2200//Console.WriteLine("Camera Eye ={0}", cameraEyeOffset);
2201
2202 //NOTE: SendSitResponse should be relative to the GROUP *NOT* THE PRIM if we're sitting on a child
2203 ControllingClient.SendSitResponse(part.ParentGroup.UUID, ((offset * part.RotationOffset) + part.OffsetPosition), sitOrientation, autopilot, cameraAtOffset, cameraEyeOffset, forceMouselook);
2204
2205 m_requestedSitTargetUUID = part.UUID; //KF: Correct autopilot target
1900 // This calls HandleAgentSit twice, once from here, and the client calls 2206 // This calls HandleAgentSit twice, once from here, and the client calls
1901 // HandleAgentSit itself after it gets to the location 2207 // HandleAgentSit itself after it gets to the location
1902 // It doesn't get to the location until we've moved them there though 2208 // It doesn't get to the location until we've moved them there though
1903 // which happens in HandleAgentSit :P 2209 // which happens in HandleAgentSit :P
1904 m_autopilotMoving = autopilot; 2210 m_autopilotMoving = autopilot;
1905 m_autoPilotTarget = pos; 2211 m_autoPilotTarget = autopilotTarget;
1906 m_sitAtAutoTarget = autopilot; 2212 m_sitAtAutoTarget = autopilot;
2213 m_initialSitTarget = autopilotTarget;
1907 if (!autopilot) 2214 if (!autopilot)
1908 HandleAgentSit(remoteClient, UUID); 2215 HandleAgentSit(remoteClient, UUID);
1909 } 2216 }
@@ -2197,47 +2504,130 @@ namespace OpenSim.Region.Framework.Scenes
2197 { 2504 {
2198 if (part != null) 2505 if (part != null)
2199 { 2506 {
2507//Console.WriteLine("Link #{0}, Rot {1}", part.LinkNum, part.GetWorldRotation());
2200 if (part.GetAvatarOnSitTarget() == UUID) 2508 if (part.GetAvatarOnSitTarget() == UUID)
2201 { 2509 {
2510//Console.WriteLine("Scripted Sit");
2511 // Scripted sit
2202 Vector3 sitTargetPos = part.SitTargetPosition; 2512 Vector3 sitTargetPos = part.SitTargetPosition;
2203 Quaternion sitTargetOrient = part.SitTargetOrientation; 2513 Quaternion sitTargetOrient = part.SitTargetOrientation;
2204
2205 //Quaternion vq = new Quaternion(sitTargetPos.X, sitTargetPos.Y+0.2f, sitTargetPos.Z+0.2f, 0);
2206 //Quaternion nq = new Quaternion(-sitTargetOrient.X, -sitTargetOrient.Y, -sitTargetOrient.Z, sitTargetOrient.w);
2207
2208 //Quaternion result = (sitTargetOrient * vq) * nq;
2209
2210 m_pos = new Vector3(sitTargetPos.X, sitTargetPos.Y, sitTargetPos.Z); 2514 m_pos = new Vector3(sitTargetPos.X, sitTargetPos.Y, sitTargetPos.Z);
2211 m_pos += SIT_TARGET_ADJUSTMENT; 2515 m_pos += SIT_TARGET_ADJUSTMENT;
2516 if (!part.IsRoot)
2517 {
2518 m_pos *= part.RotationOffset;
2519 }
2212 m_bodyRot = sitTargetOrient; 2520 m_bodyRot = sitTargetOrient;
2213 //Rotation = sitTargetOrient;
2214 m_parentPosition = part.AbsolutePosition; 2521 m_parentPosition = part.AbsolutePosition;
2215 2522 part.IsOccupied = true;
2216 //SendTerseUpdateToAllClients(); 2523 part.ParentGroup.AddAvatar(agentID);
2217 } 2524 }
2218 else 2525 else
2219 { 2526 {
2220 m_pos -= part.AbsolutePosition; 2527 // if m_avUnscriptedSitPos is zero then Av sits above center
2528 // Else Av sits at m_avUnscriptedSitPos
2529
2530 // Non-scripted sit by Kitto Flora 21Nov09
2531 // Calculate angle of line from prim to Av
2532 Quaternion partIRot;
2533// if (part.LinkNum == 1)
2534// { // Root prim of linkset
2535// partIRot = Quaternion.Inverse(part.ParentGroup.RootPart.RotationOffset);
2536// }
2537// else
2538// { // single or child prim
2539 partIRot = Quaternion.Inverse(part.GetWorldRotation());
2540// }
2541 Vector3 sitTargetPos= part.AbsolutePosition + m_avUnscriptedSitPos;
2542 float y_diff = (m_avInitialPos.Y - sitTargetPos.Y);
2543 float x_diff = ( m_avInitialPos.X - sitTargetPos.X);
2544 if(Math.Abs(x_diff) < 0.001f) x_diff = 0.001f; // avoid div by 0
2545 if(Math.Abs(y_diff) < 0.001f) y_diff = 0.001f; // avoid pol flip at 0
2546 float sit_angle = (float)Math.Atan2( (double)y_diff, (double)x_diff);
2547 // NOTE: when sitting m_ pos and m_bodyRot are *relative* to the prim location/rotation, not 'World'.
2548 // Av sits at world euler <0,0, z>, translated by part rotation
2549 m_bodyRot = partIRot * Quaternion.CreateFromEulers(0f, 0f, sit_angle); // sit at 0,0,inv-click
2550
2221 m_parentPosition = part.AbsolutePosition; 2551 m_parentPosition = part.AbsolutePosition;
2222 } 2552 part.IsOccupied = true;
2553 part.ParentGroup.AddAvatar(agentID);
2554 m_pos = new Vector3(0f, 0f, 0.05f) + // corrections to get Sit Animation
2555 (new Vector3(0.0f, 0f, 0.61f) * partIRot) + // located on center
2556 (new Vector3(0.34f, 0f, 0.0f) * m_bodyRot) +
2557 m_avUnscriptedSitPos; // adds click offset, if any
2558 //Set up raytrace to find top surface of prim
2559 Vector3 size = part.Scale;
2560 float mag = 2.0f; // 0.1f + (float)Math.Sqrt((size.X * size.X) + (size.Y * size.Y) + (size.Z * size.Z));
2561 Vector3 start = part.AbsolutePosition + new Vector3(0f, 0f, mag);
2562 Vector3 down = new Vector3(0f, 0f, -1f);
2563//Console.WriteLine("st={0} do={1} ma={2}", start, down, mag);
2564 m_scene.PhysicsScene.RaycastWorld(
2565 start, // Vector3 position,
2566 down, // Vector3 direction,
2567 mag, // float length,
2568 SitAltitudeCallback); // retMethod
2569 } // end scripted/not
2223 } 2570 }
2224 else 2571 else // no Av
2225 { 2572 {
2226 return; 2573 return;
2227 } 2574 }
2228 } 2575 }
2229 m_parentID = m_requestedSitTargetID;
2230 2576
2577 //We want our offsets to reference the root prim, not the child we may have sat on
2578 if (!part.IsRoot)
2579 {
2580 m_parentID = part.ParentGroup.RootPart.LocalId;
2581 m_pos += part.OffsetPosition;
2582 }
2583 else
2584 {
2585 m_parentID = m_requestedSitTargetID;
2586 }
2587
2588 m_linkedPrim = part.UUID;
2589 if (part.GetAvatarOnSitTarget() != UUID)
2590 {
2591 m_offsetRotation = m_offsetRotation / part.RotationOffset;
2592 }
2231 Velocity = Vector3.Zero; 2593 Velocity = Vector3.Zero;
2232 RemoveFromPhysicalScene(); 2594 RemoveFromPhysicalScene();
2233
2234 Animator.TrySetMovementAnimation(sitAnimation); 2595 Animator.TrySetMovementAnimation(sitAnimation);
2235 SendAvatarDataToAllAgents(); 2596 SendAvatarDataToAllAgents();
2236 // This may seem stupid, but Our Full updates don't send avatar rotation :P
2237 // So we're also sending a terse update (which has avatar rotation)
2238 // [Update] We do now.
2239 //SendTerseUpdateToAllClients(); 2597 //SendTerseUpdateToAllClients();
2240 } 2598 }
2599
2600 public void SitAltitudeCallback(bool hitYN, Vector3 collisionPoint, uint localid, float distance, Vector3 normal)
2601 {
2602 // KF: 091202 There appears to be a bug in Prim Edit Size - the process sometimes make a prim that RayTrace no longer
2603 // sees. Take/re-rez, or sim restart corrects the condition. Result of bug is incorrect sit height.
2604 if(hitYN)
2605 {
2606 // m_pos = Av offset from prim center to make look like on center
2607 // m_parentPosition = Actual center pos of prim
2608 // collisionPoint = spot on prim where we want to sit
2609 // collisionPoint.Z = global sit surface height
2610 SceneObjectPart part = m_scene.GetSceneObjectPart(localid);
2611 Quaternion partIRot;
2612// if (part.LinkNum == 1)
2613/// { // Root prim of linkset
2614// partIRot = Quaternion.Inverse(part.ParentGroup.RootPart.RotationOffset);
2615// }
2616// else
2617// { // single or child prim
2618 partIRot = Quaternion.Inverse(part.GetWorldRotation());
2619// }
2620 if (m_initialSitTarget != null)
2621 {
2622 float offZ = collisionPoint.Z - m_initialSitTarget.Z;
2623 Vector3 offset = new Vector3(0.0f, 0.0f, offZ) * partIRot; // Altitude correction
2624 //Console.WriteLine("sitPoint={0}, offset={1}", sitPoint, offset);
2625 m_pos += offset;
2626 // ControllingClient.SendClearFollowCamProperties(part.UUID);
2627 }
2628
2629 }
2630 } // End SitAltitudeCallback KF.
2241 2631
2242 /// <summary> 2632 /// <summary>
2243 /// Event handler for the 'Always run' setting on the client 2633 /// Event handler for the 'Always run' setting on the client
@@ -2267,12 +2657,13 @@ namespace OpenSim.Region.Framework.Scenes
2267 /// </summary> 2657 /// </summary>
2268 /// <param name="vec">The vector in which to move. This is relative to the rotation argument</param> 2658 /// <param name="vec">The vector in which to move. This is relative to the rotation argument</param>
2269 /// <param name="rotation">The direction in which this avatar should now face. 2659 /// <param name="rotation">The direction in which this avatar should now face.
2270 public void AddNewMovement(Vector3 vec, Quaternion rotation) 2660 public void AddNewMovement(Vector3 vec, Quaternion rotation, bool Nudging)
2271 { 2661 {
2272 if (m_isChildAgent) 2662 if (m_isChildAgent)
2273 { 2663 {
2274 // WHAT??? 2664 // WHAT???
2275 m_log.Debug("[SCENEPRESENCE]: AddNewMovement() called on child agent, making root agent!"); 2665 m_log.Debug("[SCENEPRESENCE]: AddNewMovement() called on child agent");
2666
2276 return; 2667 return;
2277 } 2668 }
2278 2669
@@ -2281,15 +2672,26 @@ namespace OpenSim.Region.Framework.Scenes
2281 Rotation = rotation; 2672 Rotation = rotation;
2282 Vector3 direc = vec * rotation; 2673 Vector3 direc = vec * rotation;
2283 direc.Normalize(); 2674 direc.Normalize();
2675 PhysicsActor actor = m_physicsActor;
2676
2677 if (actor.Flying != m_flyingOld) // add for fly velocity control
2678 {
2679 m_flyingOld = actor.Flying; // add for fly velocity control
2680 if (!actor.Flying) m_wasFlying = true; // add for fly velocity control
2681 }
2682
2683 if (m_physicsActor.IsColliding == true) m_wasFlying = false; // add for fly velocity control
2684
2685 if ((vec.Z == 0f) && !actor.Flying) direc.Z = 0f; // Prevent camera WASD up.
2284 2686
2285 direc *= 0.03f * 128f * m_speedModifier; 2687 direc *= 0.03f * 128f * m_speedModifier;
2286 2688
2287 PhysicsActor actor = m_physicsActor;
2288 if (actor != null) 2689 if (actor != null)
2289 { 2690 {
2290 if (actor.Flying) 2691 if (actor.Flying)
2291 { 2692 {
2292 direc *= 4.0f; 2693// rm speed mod direc *= 4.0f;
2694 direc *= 5.2f; // for speed mod
2293 //bool controlland = (((m_AgentControlFlags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_UP_NEG) != 0) || ((m_AgentControlFlags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_UP_NEG) != 0)); 2695 //bool controlland = (((m_AgentControlFlags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_UP_NEG) != 0) || ((m_AgentControlFlags & (uint)AgentManager.ControlFlags.AGENT_CONTROL_NUDGE_UP_NEG) != 0));
2294 //bool colliding = (m_physicsActor.IsColliding==true); 2696 //bool colliding = (m_physicsActor.IsColliding==true);
2295 //if (controlland) 2697 //if (controlland)
@@ -2302,22 +2704,34 @@ namespace OpenSim.Region.Framework.Scenes
2302 // m_log.Info("[AGENT]: Stop FLying"); 2704 // m_log.Info("[AGENT]: Stop FLying");
2303 //} 2705 //}
2304 } 2706 }
2707 if (Animator.m_falling && m_wasFlying) // if falling from flying, disable motion add
2708 {
2709 direc *= 0.0f;
2710 }
2711 /* This jumping section removed to SPA
2305 else if (!actor.Flying && actor.IsColliding) 2712 else if (!actor.Flying && actor.IsColliding)
2306 { 2713 {
2307 if (direc.Z > 2.0f) 2714 if (direc.Z > 2.0f)
2308 { 2715 {
2309 direc.Z *= 3.0f; 2716 if(m_animator.m_animTickJump == -1)
2310 2717 {
2311 // TODO: PreJump and jump happen too quickly. Many times prejump gets ignored. 2718 direc.Z *= 3.0f; // jump
2312 Animator.TrySetMovementAnimation("PREJUMP"); 2719 }
2313 Animator.TrySetMovementAnimation("JUMP"); 2720 else
2721 {
2722 direc.Z *= 0.1f; // prejump
2723 }
2724 / * Animations are controlled via GetMovementAnimation() in ScenePresenceAnimator.cs
2725 Animator.TrySetMovementAnimation("PREJUMP");
2726 Animator.TrySetMovementAnimation("JUMP");
2727 * /
2314 } 2728 }
2315 } 2729 } */
2316 } 2730 }
2317 2731
2318 // TODO: Add the force instead of only setting it to support multiple forces per frame? 2732 // TODO: Add the force instead of only setting it to support multiple forces per frame?
2319 m_forceToApply = direc; 2733 m_forceToApply = direc;
2320 2734 m_isNudging = Nudging;
2321 m_scene.StatsReporter.AddAgentTime(Util.EnvironmentTickCountSubtract(m_perfMonMS)); 2735 m_scene.StatsReporter.AddAgentTime(Util.EnvironmentTickCountSubtract(m_perfMonMS));
2322 } 2736 }
2323 2737
@@ -2366,6 +2780,9 @@ namespace OpenSim.Region.Framework.Scenes
2366 2780
2367 CheckForSignificantMovement(); // sends update to the modules. 2781 CheckForSignificantMovement(); // sends update to the modules.
2368 } 2782 }
2783
2784 //Sending prim updates AFTER the avatar terse updates are sent
2785 SendPrimUpdates();
2369 } 2786 }
2370 2787
2371 #endregion 2788 #endregion
@@ -3180,6 +3597,7 @@ namespace OpenSim.Region.Framework.Scenes
3180 m_callbackURI = cAgent.CallbackURI; 3597 m_callbackURI = cAgent.CallbackURI;
3181 3598
3182 m_pos = cAgent.Position; 3599 m_pos = cAgent.Position;
3600
3183 m_velocity = cAgent.Velocity; 3601 m_velocity = cAgent.Velocity;
3184 m_CameraCenter = cAgent.Center; 3602 m_CameraCenter = cAgent.Center;
3185 m_CameraAtAxis = cAgent.AtAxis; 3603 m_CameraAtAxis = cAgent.AtAxis;
@@ -3268,17 +3686,45 @@ namespace OpenSim.Region.Framework.Scenes
3268 /// </summary> 3686 /// </summary>
3269 public override void UpdateMovement() 3687 public override void UpdateMovement()
3270 { 3688 {
3271 if (m_forceToApply.HasValue) 3689 if (Animator!=null) // add for jumping
3272 { 3690 { // add for jumping
3273 Vector3 force = m_forceToApply.Value; 3691 // if (!m_animator.m_jumping) // add for jumping
3274 3692 // { // add for jumping
3275 m_updateflag = true;
3276 3693
3277 Velocity = force; 3694 if (m_forceToApply.HasValue) // this section realigned
3695 {
3278 3696
3279 m_forceToApply = null; 3697 Vector3 force = m_forceToApply.Value;
3280 } 3698 m_updateflag = true;
3281 } 3699if (m_animator.m_jumping) force.Z = m_animator.m_jumpVelocity; // add for jumping
3700 Velocity = force;
3701//Console.WriteLine("UM1 {0}", Velocity);
3702 m_forceToApply = null;
3703 }
3704 else
3705 {
3706 if (m_isNudging)
3707 {
3708 Vector3 force = Vector3.Zero;
3709
3710 m_updateflag = true;
3711if (m_animator.m_jumping) force.Z = m_animator.m_jumpVelocity; // add for jumping
3712 Velocity = force;
3713//Console.WriteLine("UM2 {0}", Velocity);
3714 m_isNudging = false;
3715 m_updateCount = UPDATE_COUNT; //KF: Update anims to pickup "STAND"
3716 }
3717 else // add for jumping
3718 { // add for jumping
3719 Vector3 force = Vector3.Zero; // add for jumping
3720if (m_animator.m_jumping) force.Z = m_animator.m_jumpVelocity; // add for jumping
3721//Console.WriteLine("UM3 {0}", Velocity);
3722 Velocity = force; // add for jumping
3723 }
3724 }
3725 // } // end realign
3726 } // add for jumping
3727 } // add for jumping
3282 3728
3283 /// <summary> 3729 /// <summary>
3284 /// Adds a physical representation of the avatar to the Physics plugin 3730 /// Adds a physical representation of the avatar to the Physics plugin
@@ -3292,10 +3738,8 @@ namespace OpenSim.Region.Framework.Scenes
3292 3738
3293 Vector3 pVec = AbsolutePosition; 3739 Vector3 pVec = AbsolutePosition;
3294 3740
3295 // Old bug where the height was in centimeters instead of meters 3741 m_physicsActor = scene.AddAvatar(Firstname + "." + Lastname, pVec,
3296 m_physicsActor = scene.AddAvatar(LocalId, Firstname + "." + Lastname, pVec,
3297 new Vector3(0f, 0f, m_appearance.AvatarHeight), isFlying); 3742 new Vector3(0f, 0f, m_appearance.AvatarHeight), isFlying);
3298
3299 scene.AddPhysicsActorTaint(m_physicsActor); 3743 scene.AddPhysicsActorTaint(m_physicsActor);
3300 //m_physicsActor.OnRequestTerseUpdate += SendTerseUpdateToAllClients; 3744 //m_physicsActor.OnRequestTerseUpdate += SendTerseUpdateToAllClients;
3301 m_physicsActor.OnCollisionUpdate += PhysicsCollisionUpdate; 3745 m_physicsActor.OnCollisionUpdate += PhysicsCollisionUpdate;
@@ -3319,18 +3763,29 @@ namespace OpenSim.Region.Framework.Scenes
3319 { 3763 {
3320 if (e == null) 3764 if (e == null)
3321 return; 3765 return;
3322 3766
3323 //if ((Math.Abs(Velocity.X) > 0.1e-9f) || (Math.Abs(Velocity.Y) > 0.1e-9f)) 3767 // The Physics Scene will send (spam!) updates every 500 ms grep: m_physicsActor.SubscribeEvents(
3324 // The Physics Scene will send updates every 500 ms grep: m_physicsActor.SubscribeEvents(
3325 // as of this comment the interval is set in AddToPhysicalScene 3768 // as of this comment the interval is set in AddToPhysicalScene
3326 if (Animator!=null) 3769 if (Animator!=null)
3327 Animator.UpdateMovementAnimations(); 3770 {
3771 if (m_updateCount > 0) //KF: DO NOT call UpdateMovementAnimations outside of the m_updateCount wrapper,
3772 { // else its will lock out other animation changes, like ground sit.
3773 Animator.UpdateMovementAnimations();
3774 m_updateCount--;
3775 }
3776 }
3328 3777
3329 CollisionEventUpdate collisionData = (CollisionEventUpdate)e; 3778 CollisionEventUpdate collisionData = (CollisionEventUpdate)e;
3330 Dictionary<uint, ContactPoint> coldata = collisionData.m_objCollisionList; 3779 Dictionary<uint, ContactPoint> coldata = collisionData.m_objCollisionList;
3331 3780
3332 CollisionPlane = Vector4.UnitW; 3781 CollisionPlane = Vector4.UnitW;
3333 3782
3783 if (m_lastColCount != coldata.Count)
3784 {
3785 m_updateCount = UPDATE_COUNT;
3786 m_lastColCount = coldata.Count;
3787 }
3788
3334 if (coldata.Count != 0 && Animator != null) 3789 if (coldata.Count != 0 && Animator != null)
3335 { 3790 {
3336 switch (Animator.CurrentMovementAnimation) 3791 switch (Animator.CurrentMovementAnimation)
@@ -3360,6 +3815,148 @@ namespace OpenSim.Region.Framework.Scenes
3360 } 3815 }
3361 } 3816 }
3362 3817
3818 List<uint> thisHitColliders = new List<uint>();
3819 List<uint> endedColliders = new List<uint>();
3820 List<uint> startedColliders = new List<uint>();
3821
3822 foreach (uint localid in coldata.Keys)
3823 {
3824 thisHitColliders.Add(localid);
3825 if (!m_lastColliders.Contains(localid))
3826 {
3827 startedColliders.Add(localid);
3828 }
3829 //m_log.Debug("[SCENE PRESENCE]: Collided with:" + localid.ToString() + " at depth of: " + collissionswith[localid].ToString());
3830 }
3831
3832 // calculate things that ended colliding
3833 foreach (uint localID in m_lastColliders)
3834 {
3835 if (!thisHitColliders.Contains(localID))
3836 {
3837 endedColliders.Add(localID);
3838 }
3839 }
3840 //add the items that started colliding this time to the last colliders list.
3841 foreach (uint localID in startedColliders)
3842 {
3843 m_lastColliders.Add(localID);
3844 }
3845 // remove things that ended colliding from the last colliders list
3846 foreach (uint localID in endedColliders)
3847 {
3848 m_lastColliders.Remove(localID);
3849 }
3850
3851 // do event notification
3852 if (startedColliders.Count > 0)
3853 {
3854 ColliderArgs StartCollidingMessage = new ColliderArgs();
3855 List<DetectedObject> colliding = new List<DetectedObject>();
3856 foreach (uint localId in startedColliders)
3857 {
3858 if (localId == 0)
3859 continue;
3860
3861 SceneObjectPart obj = Scene.GetSceneObjectPart(localId);
3862 string data = "";
3863 if (obj != null)
3864 {
3865 DetectedObject detobj = new DetectedObject();
3866 detobj.keyUUID = obj.UUID;
3867 detobj.nameStr = obj.Name;
3868 detobj.ownerUUID = obj.OwnerID;
3869 detobj.posVector = obj.AbsolutePosition;
3870 detobj.rotQuat = obj.GetWorldRotation();
3871 detobj.velVector = obj.Velocity;
3872 detobj.colliderType = 0;
3873 detobj.groupUUID = obj.GroupID;
3874 colliding.Add(detobj);
3875 }
3876 }
3877
3878 if (colliding.Count > 0)
3879 {
3880 StartCollidingMessage.Colliders = colliding;
3881
3882 foreach (SceneObjectGroup att in Attachments)
3883 Scene.EventManager.TriggerScriptCollidingStart(att.LocalId, StartCollidingMessage);
3884 }
3885 }
3886
3887 if (endedColliders.Count > 0)
3888 {
3889 ColliderArgs EndCollidingMessage = new ColliderArgs();
3890 List<DetectedObject> colliding = new List<DetectedObject>();
3891 foreach (uint localId in endedColliders)
3892 {
3893 if (localId == 0)
3894 continue;
3895
3896 SceneObjectPart obj = Scene.GetSceneObjectPart(localId);
3897 string data = "";
3898 if (obj != null)
3899 {
3900 DetectedObject detobj = new DetectedObject();
3901 detobj.keyUUID = obj.UUID;
3902 detobj.nameStr = obj.Name;
3903 detobj.ownerUUID = obj.OwnerID;
3904 detobj.posVector = obj.AbsolutePosition;
3905 detobj.rotQuat = obj.GetWorldRotation();
3906 detobj.velVector = obj.Velocity;
3907 detobj.colliderType = 0;
3908 detobj.groupUUID = obj.GroupID;
3909 colliding.Add(detobj);
3910 }
3911 }
3912
3913 if (colliding.Count > 0)
3914 {
3915 EndCollidingMessage.Colliders = colliding;
3916
3917 foreach (SceneObjectGroup att in Attachments)
3918 Scene.EventManager.TriggerScriptCollidingEnd(att.LocalId, EndCollidingMessage);
3919 }
3920 }
3921
3922 if (thisHitColliders.Count > 0)
3923 {
3924 ColliderArgs CollidingMessage = new ColliderArgs();
3925 List<DetectedObject> colliding = new List<DetectedObject>();
3926 foreach (uint localId in thisHitColliders)
3927 {
3928 if (localId == 0)
3929 continue;
3930
3931 SceneObjectPart obj = Scene.GetSceneObjectPart(localId);
3932 string data = "";
3933 if (obj != null)
3934 {
3935 DetectedObject detobj = new DetectedObject();
3936 detobj.keyUUID = obj.UUID;
3937 detobj.nameStr = obj.Name;
3938 detobj.ownerUUID = obj.OwnerID;
3939 detobj.posVector = obj.AbsolutePosition;
3940 detobj.rotQuat = obj.GetWorldRotation();
3941 detobj.velVector = obj.Velocity;
3942 detobj.colliderType = 0;
3943 detobj.groupUUID = obj.GroupID;
3944 colliding.Add(detobj);
3945 }
3946 }
3947
3948 if (colliding.Count > 0)
3949 {
3950 CollidingMessage.Colliders = colliding;
3951
3952 lock (m_attachments)
3953 {
3954 foreach (SceneObjectGroup att in m_attachments)
3955 Scene.EventManager.TriggerScriptColliding(att.LocalId, CollidingMessage);
3956 }
3957 }
3958 }
3959
3363 if (m_invulnerable) 3960 if (m_invulnerable)
3364 return; 3961 return;
3365 3962
@@ -3444,6 +4041,10 @@ namespace OpenSim.Region.Framework.Scenes
3444 { 4041 {
3445 lock (m_attachments) 4042 lock (m_attachments)
3446 { 4043 {
4044 // This may be true when the attachment comes back
4045 // from serialization after login. Clear it.
4046 gobj.IsDeleted = false;
4047
3447 m_attachments.Add(gobj); 4048 m_attachments.Add(gobj);
3448 } 4049 }
3449 } 4050 }
@@ -3785,6 +4386,39 @@ namespace OpenSim.Region.Framework.Scenes
3785 return; 4386 return;
3786 } 4387 }
3787 4388
4389 XmlDocument doc = new XmlDocument();
4390 string stateData = String.Empty;
4391
4392 IAttachmentsService attServ = m_scene.RequestModuleInterface<IAttachmentsService>();
4393 if (attServ != null)
4394 {
4395 m_log.DebugFormat("[ATTACHMENT]: Loading attachment data from attachment service");
4396 stateData = attServ.Get(ControllingClient.AgentId.ToString());
4397 if (stateData != String.Empty)
4398 {
4399 try
4400 {
4401 doc.LoadXml(stateData);
4402 }
4403 catch { }
4404 }
4405 }
4406
4407 Dictionary<UUID, string> itemData = new Dictionary<UUID, string>();
4408
4409 XmlNodeList nodes = doc.GetElementsByTagName("Attachment");
4410 if (nodes.Count > 0)
4411 {
4412 foreach (XmlNode n in nodes)
4413 {
4414 XmlElement elem = (XmlElement)n;
4415 string itemID = elem.GetAttribute("ItemID");
4416 string xml = elem.InnerXml;
4417
4418 itemData[new UUID(itemID)] = xml;
4419 }
4420 }
4421
3788 List<AvatarAttachment> attachments = m_appearance.GetAttachments(); 4422 List<AvatarAttachment> attachments = m_appearance.GetAttachments();
3789 foreach (AvatarAttachment attach in attachments) 4423 foreach (AvatarAttachment attach in attachments)
3790 { 4424 {
@@ -3805,7 +4439,30 @@ namespace OpenSim.Region.Framework.Scenes
3805 4439
3806 try 4440 try
3807 { 4441 {
3808 m_scene.AttachmentsModule.RezSingleAttachmentFromInventory(ControllingClient, itemID, (uint)p); 4442 string xmlData;
4443 XmlDocument d = new XmlDocument();
4444 UUID asset;
4445 if (itemData.TryGetValue(itemID, out xmlData))
4446 {
4447 d.LoadXml(xmlData);
4448 m_log.InfoFormat("[ATTACHMENT]: Found saved state for item {0}, loading it", itemID);
4449
4450 // Rez from inventory
4451 asset
4452 = m_scene.AttachmentsModule.RezSingleAttachmentFromInventory(ControllingClient, itemID, (uint)p, true, d);
4453
4454 }
4455 else
4456 {
4457 // Rez from inventory (with a null doc to let
4458 // CHANGED_OWNER happen)
4459 asset
4460 = m_scene.AttachmentsModule.RezSingleAttachmentFromInventory(ControllingClient, itemID, (uint)p, true, null);
4461 }
4462
4463 m_log.InfoFormat(
4464 "[ATTACHMENT]: Rezzed attachment in point {0} from item {1} and asset {2}",
4465 p, itemID, asset);
3809 } 4466 }
3810 catch (Exception e) 4467 catch (Exception e)
3811 { 4468 {
@@ -3838,6 +4495,15 @@ namespace OpenSim.Region.Framework.Scenes
3838 m_reprioritization_called = false; 4495 m_reprioritization_called = false;
3839 } 4496 }
3840 } 4497 }
4498
4499 private Vector3 Quat2Euler(Quaternion rot){
4500 float x = Utils.RAD_TO_DEG * (float)Math.Atan2((double)((2.0f * rot.X * rot.W) - (2.0f * rot.Y * rot.Z)) ,
4501 (double)(1 - (2.0f * rot.X * rot.X) - (2.0f * rot.Z * rot.Z)));
4502 float y = Utils.RAD_TO_DEG * (float)Math.Asin ((double)((2.0f * rot.X * rot.Y) + (2.0f * rot.Z * rot.W)));
4503 float z = Utils.RAD_TO_DEG * (float)Math.Atan2(((double)(2.0f * rot.Y * rot.W) - (2.0f * rot.X * rot.Z)) ,
4504 (double)(1 - (2.0f * rot.Y * rot.Y) - (2.0f * rot.Z * rot.Z)));
4505 return(new Vector3(x,y,z));
4506 }
3841 4507
3842 public void SaveChangedAttachments() 4508 public void SaveChangedAttachments()
3843 { 4509 {
@@ -3861,5 +4527,30 @@ namespace OpenSim.Region.Framework.Scenes
3861 } 4527 }
3862 } 4528 }
3863 } 4529 }
4530
4531 private void CheckLandingPoint(ref Vector3 pos)
4532 {
4533 // Never constrain lures
4534 if ((TeleportFlags & TeleportFlags.ViaLure) != 0)
4535 return;
4536
4537 if (m_scene.RegionInfo.EstateSettings.AllowDirectTeleport)
4538 return;
4539
4540 ILandObject land = m_scene.LandChannel.GetLandObject(pos.X, pos.Y);
4541
4542 if (land.LandData.LandingType == (byte)LandingType.LandingPoint &&
4543 land.LandData.UserLocation != Vector3.Zero &&
4544 land.LandData.OwnerID != m_uuid &&
4545 (!m_scene.Permissions.IsGod(m_uuid)) &&
4546 (!m_scene.RegionInfo.EstateSettings.IsEstateManager(m_uuid)))
4547 {
4548 float curr = Vector3.Distance(AbsolutePosition, pos);
4549 if (Vector3.Distance(land.LandData.UserLocation, pos) < curr)
4550 pos = land.LandData.UserLocation;
4551 else
4552 ControllingClient.SendAlertMessage("Can't teleport closer to destination");
4553 }
4554 }
3864 } 4555 }
3865} 4556}