Reuse the same AgentUpdateArgs object for each AgentUpdate UDP packet (of which there are 10 a second) rather than constructing a new one every time.
We can do this because AgentUpdate packets are handled synchronously.0.7.4-extended
parent
73c2db9e8f
commit
8726748e22
|
@ -91,8 +91,23 @@ namespace OpenSim.Region.ClientStack.LindenUDP
|
||||||
public event ObjectDeselect OnObjectDetach;
|
public event ObjectDeselect OnObjectDetach;
|
||||||
public event ObjectDrop OnObjectDrop;
|
public event ObjectDrop OnObjectDrop;
|
||||||
public event Action<IClientAPI, bool> OnCompleteMovementToRegion;
|
public event Action<IClientAPI, bool> OnCompleteMovementToRegion;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Called when an AgentUpdate message is received and before OnAgentUpdate.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// Listeners must not retain a reference to AgentUpdateArgs since this object is reused for subsequent AgentUpdates.
|
||||||
|
/// </remarks>
|
||||||
public event UpdateAgent OnPreAgentUpdate;
|
public event UpdateAgent OnPreAgentUpdate;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Called when an AgentUpdate message is received and after OnPreAgentUpdate.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// Listeners must not retain a reference to AgentUpdateArgs since this object is reused for subsequent AgentUpdates.
|
||||||
|
/// </remarks>
|
||||||
public event UpdateAgent OnAgentUpdate;
|
public event UpdateAgent OnAgentUpdate;
|
||||||
|
|
||||||
public event AgentRequestSit OnAgentRequestSit;
|
public event AgentRequestSit OnAgentRequestSit;
|
||||||
public event AgentSit OnAgentSit;
|
public event AgentSit OnAgentSit;
|
||||||
public event AvatarPickerRequest OnAvatarPickerRequest;
|
public event AvatarPickerRequest OnAvatarPickerRequest;
|
||||||
|
@ -346,7 +361,17 @@ namespace OpenSim.Region.ClientStack.LindenUDP
|
||||||
private int m_moneyBalance;
|
private int m_moneyBalance;
|
||||||
private int m_animationSequenceNumber = 1;
|
private int m_animationSequenceNumber = 1;
|
||||||
private bool m_SendLogoutPacketWhenClosing = true;
|
private bool m_SendLogoutPacketWhenClosing = true;
|
||||||
private AgentUpdateArgs lastarg;
|
|
||||||
|
/// <summary>
|
||||||
|
/// We retain a single AgentUpdateArgs so that we can constantly reuse it rather than construct a new one for
|
||||||
|
/// every single incoming AgentUpdate. Every client sends 10 AgentUpdate UDP messages per second, even if it
|
||||||
|
/// is doing absolutely nothing.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// This does mean that agent updates must be processed synchronously, at least for each client, and called methods
|
||||||
|
/// cannot retain a reference to it outside of that method.
|
||||||
|
/// </remarks>
|
||||||
|
private AgentUpdateArgs m_lastAgentUpdateArgs;
|
||||||
|
|
||||||
protected Dictionary<PacketType, PacketProcessor> m_packetHandlers = new Dictionary<PacketType, PacketProcessor>();
|
protected Dictionary<PacketType, PacketProcessor> m_packetHandlers = new Dictionary<PacketType, PacketProcessor>();
|
||||||
protected Dictionary<string, GenericMessage> m_genericPacketHandlers = new Dictionary<string, GenericMessage>(); //PauPaw:Local Generic Message handlers
|
protected Dictionary<string, GenericMessage> m_genericPacketHandlers = new Dictionary<string, GenericMessage>(); //PauPaw:Local Generic Message handlers
|
||||||
|
@ -5197,7 +5222,11 @@ namespace OpenSim.Region.ClientStack.LindenUDP
|
||||||
protected virtual void RegisterLocalPacketHandlers()
|
protected virtual void RegisterLocalPacketHandlers()
|
||||||
{
|
{
|
||||||
AddLocalPacketHandler(PacketType.LogoutRequest, HandleLogout);
|
AddLocalPacketHandler(PacketType.LogoutRequest, HandleLogout);
|
||||||
|
|
||||||
|
// If AgentUpdate is ever handled asynchronously, then we will also need to construct a new AgentUpdateArgs
|
||||||
|
// for each AgentUpdate packet.
|
||||||
AddLocalPacketHandler(PacketType.AgentUpdate, HandleAgentUpdate, false);
|
AddLocalPacketHandler(PacketType.AgentUpdate, HandleAgentUpdate, false);
|
||||||
|
|
||||||
AddLocalPacketHandler(PacketType.ViewerEffect, HandleViewerEffect, false);
|
AddLocalPacketHandler(PacketType.ViewerEffect, HandleViewerEffect, false);
|
||||||
AddLocalPacketHandler(PacketType.AgentCachedTexture, HandleAgentTextureCached, false);
|
AddLocalPacketHandler(PacketType.AgentCachedTexture, HandleAgentTextureCached, false);
|
||||||
AddLocalPacketHandler(PacketType.MultipleObjectUpdate, HandleMultipleObjUpdate, false);
|
AddLocalPacketHandler(PacketType.MultipleObjectUpdate, HandleMultipleObjUpdate, false);
|
||||||
|
@ -5428,73 +5457,71 @@ namespace OpenSim.Region.ClientStack.LindenUDP
|
||||||
{
|
{
|
||||||
if (OnAgentUpdate != null)
|
if (OnAgentUpdate != null)
|
||||||
{
|
{
|
||||||
bool update = false;
|
AgentUpdatePacket agentUpdate = (AgentUpdatePacket)packet;
|
||||||
AgentUpdatePacket agenUpdate = (AgentUpdatePacket)packet;
|
|
||||||
|
|
||||||
#region Packet Session and User Check
|
#region Packet Session and User Check
|
||||||
if (agenUpdate.AgentData.SessionID != SessionId || agenUpdate.AgentData.AgentID != AgentId)
|
if (agentUpdate.AgentData.SessionID != SessionId || agentUpdate.AgentData.AgentID != AgentId)
|
||||||
{
|
{
|
||||||
PacketPool.Instance.ReturnPacket(packet);
|
PacketPool.Instance.ReturnPacket(packet);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
AgentUpdatePacket.AgentDataBlock x = agenUpdate.AgentData;
|
bool update = false;
|
||||||
|
AgentUpdatePacket.AgentDataBlock x = agentUpdate.AgentData;
|
||||||
|
|
||||||
// We can only check when we have something to check
|
if (m_lastAgentUpdateArgs != null)
|
||||||
// against.
|
|
||||||
|
|
||||||
if (lastarg != null)
|
|
||||||
{
|
{
|
||||||
|
// These should be ordered from most-likely to
|
||||||
|
// least likely to change. I've made an initial
|
||||||
|
// guess at that.
|
||||||
update =
|
update =
|
||||||
(
|
(
|
||||||
(x.BodyRotation != lastarg.BodyRotation) ||
|
(x.BodyRotation != m_lastAgentUpdateArgs.BodyRotation) ||
|
||||||
(x.CameraAtAxis != lastarg.CameraAtAxis) ||
|
(x.CameraAtAxis != m_lastAgentUpdateArgs.CameraAtAxis) ||
|
||||||
(x.CameraCenter != lastarg.CameraCenter) ||
|
(x.CameraCenter != m_lastAgentUpdateArgs.CameraCenter) ||
|
||||||
(x.CameraLeftAxis != lastarg.CameraLeftAxis) ||
|
(x.CameraLeftAxis != m_lastAgentUpdateArgs.CameraLeftAxis) ||
|
||||||
(x.CameraUpAxis != lastarg.CameraUpAxis) ||
|
(x.CameraUpAxis != m_lastAgentUpdateArgs.CameraUpAxis) ||
|
||||||
(x.ControlFlags != lastarg.ControlFlags) ||
|
(x.ControlFlags != m_lastAgentUpdateArgs.ControlFlags) ||
|
||||||
(x.Far != lastarg.Far) ||
|
(x.Far != m_lastAgentUpdateArgs.Far) ||
|
||||||
(x.Flags != lastarg.Flags) ||
|
(x.Flags != m_lastAgentUpdateArgs.Flags) ||
|
||||||
(x.State != lastarg.State) ||
|
(x.State != m_lastAgentUpdateArgs.State) ||
|
||||||
(x.HeadRotation != lastarg.HeadRotation) ||
|
(x.HeadRotation != m_lastAgentUpdateArgs.HeadRotation) ||
|
||||||
(x.SessionID != lastarg.SessionID) ||
|
(x.SessionID != m_lastAgentUpdateArgs.SessionID) ||
|
||||||
(x.AgentID != lastarg.AgentID)
|
(x.AgentID != m_lastAgentUpdateArgs.AgentID)
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
m_lastAgentUpdateArgs = new AgentUpdateArgs();
|
||||||
update = true;
|
update = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
// These should be ordered from most-likely to
|
|
||||||
// least likely to change. I've made an initial
|
|
||||||
// guess at that.
|
|
||||||
|
|
||||||
if (update)
|
if (update)
|
||||||
{
|
{
|
||||||
// m_log.DebugFormat("[LLCLIENTVIEW]: Triggered AgentUpdate for {0}", sener.Name);
|
// m_log.DebugFormat("[LLCLIENTVIEW]: Triggered AgentUpdate for {0}", sener.Name);
|
||||||
|
|
||||||
AgentUpdateArgs arg = new AgentUpdateArgs();
|
m_lastAgentUpdateArgs.AgentID = x.AgentID;
|
||||||
arg.AgentID = x.AgentID;
|
m_lastAgentUpdateArgs.BodyRotation = x.BodyRotation;
|
||||||
arg.BodyRotation = x.BodyRotation;
|
m_lastAgentUpdateArgs.CameraAtAxis = x.CameraAtAxis;
|
||||||
arg.CameraAtAxis = x.CameraAtAxis;
|
m_lastAgentUpdateArgs.CameraCenter = x.CameraCenter;
|
||||||
arg.CameraCenter = x.CameraCenter;
|
m_lastAgentUpdateArgs.CameraLeftAxis = x.CameraLeftAxis;
|
||||||
arg.CameraLeftAxis = x.CameraLeftAxis;
|
m_lastAgentUpdateArgs.CameraUpAxis = x.CameraUpAxis;
|
||||||
arg.CameraUpAxis = x.CameraUpAxis;
|
m_lastAgentUpdateArgs.ControlFlags = x.ControlFlags;
|
||||||
arg.ControlFlags = x.ControlFlags;
|
m_lastAgentUpdateArgs.Far = x.Far;
|
||||||
arg.Far = x.Far;
|
m_lastAgentUpdateArgs.Flags = x.Flags;
|
||||||
arg.Flags = x.Flags;
|
m_lastAgentUpdateArgs.HeadRotation = x.HeadRotation;
|
||||||
arg.HeadRotation = x.HeadRotation;
|
m_lastAgentUpdateArgs.SessionID = x.SessionID;
|
||||||
arg.SessionID = x.SessionID;
|
m_lastAgentUpdateArgs.State = x.State;
|
||||||
arg.State = x.State;
|
|
||||||
UpdateAgent handlerAgentUpdate = OnAgentUpdate;
|
UpdateAgent handlerAgentUpdate = OnAgentUpdate;
|
||||||
UpdateAgent handlerPreAgentUpdate = OnPreAgentUpdate;
|
UpdateAgent handlerPreAgentUpdate = OnPreAgentUpdate;
|
||||||
lastarg = arg; // save this set of arguments for nexttime
|
|
||||||
if (handlerPreAgentUpdate != null)
|
if (handlerPreAgentUpdate != null)
|
||||||
OnPreAgentUpdate(this, arg);
|
OnPreAgentUpdate(this, m_lastAgentUpdateArgs);
|
||||||
|
|
||||||
if (handlerAgentUpdate != null)
|
if (handlerAgentUpdate != null)
|
||||||
OnAgentUpdate(this, arg);
|
OnAgentUpdate(this, m_lastAgentUpdateArgs);
|
||||||
|
|
||||||
handlerAgentUpdate = null;
|
handlerAgentUpdate = null;
|
||||||
handlerPreAgentUpdate = null;
|
handlerPreAgentUpdate = null;
|
||||||
|
|
Loading…
Reference in New Issue