reduce calls to physics world cast rays for camera collision check

melanie
UbitUmarov 2016-11-14 03:21:07 +00:00
parent 3cb2b3b2d1
commit ae17b5d203
3 changed files with 55 additions and 51 deletions

View File

@ -81,6 +81,7 @@ namespace OpenSim.Framework
public Vector3 ClientAgentPosition; public Vector3 ClientAgentPosition;
public bool UseClientAgentPosition; public bool UseClientAgentPosition;
public bool NeedsCameraCollision;
public AgentUpdateArgs() public AgentUpdateArgs()
{ {

View File

@ -6274,6 +6274,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP
m_thisAgentUpdateArgs.HeadRotation = x.HeadRotation; m_thisAgentUpdateArgs.HeadRotation = x.HeadRotation;
m_thisAgentUpdateArgs.State = x.State; m_thisAgentUpdateArgs.State = x.State;
m_thisAgentUpdateArgs.NeedsCameraCollision = !camera;
UpdateAgent handlerAgentUpdate = OnAgentUpdate; UpdateAgent handlerAgentUpdate = OnAgentUpdate;
UpdateAgent handlerPreAgentUpdate = OnPreAgentUpdate; UpdateAgent handlerPreAgentUpdate = OnPreAgentUpdate;
@ -6293,6 +6295,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP
m_thisAgentUpdateArgs.CameraLeftAxis = x.CameraLeftAxis; m_thisAgentUpdateArgs.CameraLeftAxis = x.CameraLeftAxis;
m_thisAgentUpdateArgs.CameraUpAxis = x.CameraUpAxis; m_thisAgentUpdateArgs.CameraUpAxis = x.CameraUpAxis;
m_thisAgentUpdateArgs.NeedsCameraCollision = true;
UpdateAgent handlerAgentCameraUpdate = OnAgentCameraUpdate; UpdateAgent handlerAgentCameraUpdate = OnAgentCameraUpdate;
if (handlerAgentCameraUpdate != null) if (handlerAgentCameraUpdate != null)

View File

@ -2297,6 +2297,48 @@ namespace OpenSim.Region.Framework.Scenes
/// <param name="distance"></param> /// <param name="distance"></param>
/// ///
private void checkCameraCollision()
{
if(!m_scene.PhysicsScene.SupportsRayCast())
return;
++m_movementUpdateCount;
if (m_movementUpdateCount < 1)
m_movementUpdateCount = 1;
if (m_doingCamRayCast || m_movementUpdateCount % NumMovementsBetweenRayCast != 0)
return;
if (m_followCamAuto && !m_mouseLook)
{
Vector3 posAdjusted = AbsolutePosition;
// posAdjusted.Z += 0.5f * Appearance.AvatarSize.Z - 0.5f;
posAdjusted.Z += 1.0f; // viewer current camera focus point
Vector3 tocam = CameraPosition - posAdjusted;
tocam.X = (float)Math.Round(tocam.X, 1);
tocam.Y = (float)Math.Round(tocam.Y, 1);
tocam.Z = (float)Math.Round(tocam.Z, 1);
float distTocamlen = tocam.Length();
if (distTocamlen > 0.3f)
{
tocam *= (1.0f / distTocamlen);
posAdjusted.X = (float)Math.Round(posAdjusted.X, 1);
posAdjusted.Y = (float)Math.Round(posAdjusted.Y, 1);
posAdjusted.Z = (float)Math.Round(posAdjusted.Z, 1);
m_doingCamRayCast = true;
m_scene.PhysicsScene.RaycastWorld(posAdjusted, tocam, distTocamlen + 1.0f, RayCastCameraCallback);
}
}
else if (CameraConstraintActive)
{
Vector4 plane = new Vector4(0.9f, 0.0f, 0.361f, -10000f); // not right...
UpdateCameraCollisionPlane(plane);
CameraConstraintActive = false;
}
}
private void UpdateCameraCollisionPlane(Vector4 plane) private void UpdateCameraCollisionPlane(Vector4 plane)
{ {
if (m_lastCameraCollisionPlane != plane) if (m_lastCameraCollisionPlane != plane)
@ -2442,38 +2484,8 @@ namespace OpenSim.Region.Framework.Scenes
// Raycast from the avatar's head to the camera to see if there's anything blocking the view // Raycast from the avatar's head to the camera to see if there's anything blocking the view
// this exclude checks may not be complete // this exclude checks may not be complete
if(agentData.NeedsCameraCollision && ParentID == 0) // condition parentID may be wrong
if (m_movementUpdateCount % NumMovementsBetweenRayCast == 0 && m_scene.PhysicsScene.SupportsRayCast()) checkCameraCollision();
{
if (!m_doingCamRayCast && !m_mouseLook && ParentID == 0)
{
Vector3 posAdjusted = AbsolutePosition;
// posAdjusted.Z += 0.5f * Appearance.AvatarSize.Z - 0.5f;
posAdjusted.Z += 1.0f; // viewer current camera focus point
Vector3 tocam = CameraPosition - posAdjusted;
tocam.X = (float)Math.Round(tocam.X, 1);
tocam.Y = (float)Math.Round(tocam.Y, 1);
tocam.Z = (float)Math.Round(tocam.Z, 1);
float distTocamlen = tocam.Length();
if (distTocamlen > 0.3f)
{
tocam *= (1.0f / distTocamlen);
posAdjusted.X = (float)Math.Round(posAdjusted.X, 1);
posAdjusted.Y = (float)Math.Round(posAdjusted.Y, 1);
posAdjusted.Z = (float)Math.Round(posAdjusted.Z, 1);
m_doingCamRayCast = true;
m_scene.PhysicsScene.RaycastWorld(posAdjusted, tocam, distTocamlen + 1.0f, RayCastCameraCallback);
}
}
else if (CameraConstraintActive && (m_mouseLook || ParentID != 0))
{
Vector4 plane = new Vector4(0.9f, 0.0f, 0.361f, -10000f); // not right...
UpdateCameraCollisionPlane(plane);
CameraConstraintActive = false;
}
}
uint flagsForScripts = (uint)flags; uint flagsForScripts = (uint)flags;
flags = RemoveIgnoredControls(flags, IgnoredControls); flags = RemoveIgnoredControls(flags, IgnoredControls);
@ -2742,14 +2754,10 @@ namespace OpenSim.Region.Framework.Scenes
// Scene.RegionInfo.RegionName, remoteClient.Name, (AgentManager.ControlFlags)agentData.ControlFlags); // Scene.RegionInfo.RegionName, remoteClient.Name, (AgentManager.ControlFlags)agentData.ControlFlags);
if (IsChildAgent) if (IsChildAgent)
{
// // m_log.Debug("DEBUG: HandleAgentUpdate: child agent");
return; return;
}
++m_movementUpdateCount; if(IsInTransit)
if (m_movementUpdateCount < 1) return;
m_movementUpdateCount = 1;
// AgentManager.ControlFlags flags = (AgentManager.ControlFlags)agentData.ControlFlags; // AgentManager.ControlFlags flags = (AgentManager.ControlFlags)agentData.ControlFlags;
@ -2779,17 +2787,8 @@ namespace OpenSim.Region.Framework.Scenes
m_followCamAuto = ((CameraUpAxis.Z > 0.959f && CameraUpAxis.Z < 0.98f) m_followCamAuto = ((CameraUpAxis.Z > 0.959f && CameraUpAxis.Z < 0.98f)
&& (Math.Abs(camdif.X) < 0.4f && Math.Abs(camdif.Y) < 0.4f)) ? true : false; && (Math.Abs(camdif.X) < 0.4f && Math.Abs(camdif.Y) < 0.4f)) ? true : false;
if(agentData.NeedsCameraCollision)
//m_log.DebugFormat("[FollowCam]: {0}", m_followCamAuto); checkCameraCollision();
// 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 posAdjusted = m_pos + HEAD_ADJUSTMENT;
m_scene.PhysicsScene.RaycastWorld(m_pos, Vector3.Normalize(CameraPosition - posAdjusted), Vector3.Distance(CameraPosition, posAdjusted) + 0.3f, RayCastCameraCallback);
}
}
TriggerScenePresenceUpdated(); TriggerScenePresenceUpdated();
} }