Skip to content

Commit

Permalink
proximity checker now fully works.
Browse files Browse the repository at this point in the history
  • Loading branch information
dragonslaya84 committed Nov 9, 2021
1 parent 8035029 commit a8e710c
Show file tree
Hide file tree
Showing 11 changed files with 88 additions and 161 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ public class NetworkProximityChecker : BaseVisibilityInspector

protected override void Start()
{
NetworkVisibility = new NetworkProximityCheckerVisibility(ServerObjectManager, VisibilityRange, VisibilityUpdateInterval);
NetworkVisibility = new NetworkProximityCheckerVisibility(ServerObjectManager, VisibilityRange, VisibilityUpdateInterval, Identity);

base.Start();
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ public class NetworkSceneChecker : BaseVisibilityInspector
{
protected override void Start()
{
NetworkVisibility = new SceneVisibilityChecker(ServerObjectManager);
NetworkVisibility = new SceneVisibilityChecker(ServerObjectManager, gameObject.scene, Identity);

base.Start();
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,35 +15,24 @@ namespace Mirage.Components
[HelpURL("https://miragenet.github.io/Mirage/Articles/Components/NetworkProximityChecker.html")]
public class NetworkProximityCheckerVisibility : NetworkVisibility
{
private class NetIdComparer : IEqualityComparer<NetworkIdentity>
{
public bool Equals(NetworkIdentity x, NetworkIdentity y)
{
return x.NetId == y.NetId;
}
public int GetHashCode(NetworkIdentity obj)
{
return (int)obj.NetId;
}
}

static readonly ILogger logger = LogFactory.GetLogger(typeof(NetworkProximityCheckerVisibility));

private readonly float _sightDistnace = 10;
private readonly float _updateInterval = 0;
private float _nextUpdate = 0;
private readonly Dictionary<INetworkPlayer, HashSet<NetworkIdentity>> lastFrame = new Dictionary<INetworkPlayer, HashSet<NetworkIdentity>>();
private NetworkIdentity _identity;

/// <summary>
///
/// </summary>
/// <param name="serverObjectManager"></param>
/// <param name="sightDistance"></param>
/// <param name="updateInterval"></param>
public NetworkProximityCheckerVisibility(ServerObjectManager serverObjectManager, float sightDistance, float updateInterval) : base(serverObjectManager)
public NetworkProximityCheckerVisibility(ServerObjectManager serverObjectManager, float sightDistance, float updateInterval, NetworkIdentity objectTransform) : base(serverObjectManager)
{
_sightDistnace = sightDistance;
_updateInterval = updateInterval;
_identity = objectTransform;
}

[MethodImpl(MethodImplOptions.AggressiveInlining)]
Expand All @@ -54,63 +43,6 @@ static bool FastInDistanceXZ(Vector3 a, Vector3 b, float sqRange)
float sqDist = dx * dx + dz * dz;
return sqDist < sqRange;
}
private void Rebuild()
{
foreach (NetworkIdentity identity in InterestManager.ServerObjectManager.Server.World.SpawnedIdentities)
{
foreach (INetworkPlayer player in VisibilitySystemData.Keys)
{
if (!VisibilitySystemData.TryGetValue(player, out HashSet<NetworkIdentity> nextSet))
{
nextSet = new HashSet<NetworkIdentity>(new NetIdComparer());
VisibilitySystemData[player] = nextSet;
}

nextSet.Add(identity);
}
}

foreach (INetworkPlayer player in InterestManager.ServerObjectManager.Server.Players)
{
if (!lastFrame.TryGetValue(player, out HashSet<NetworkIdentity> lastSet))
{
lastSet = new HashSet<NetworkIdentity>(new NetIdComparer());
lastFrame[player] = lastSet;
}

if (!VisibilitySystemData.TryGetValue(player, out HashSet<NetworkIdentity> nextSet))
{
nextSet = new HashSet<NetworkIdentity>(new NetIdComparer());
VisibilitySystemData[player] = nextSet;
}


foreach (NetworkIdentity identity in lastSet)
{
if (!nextSet.Contains(identity))
{
InterestManager.ServerObjectManager.HideToPlayer(identity, player);
}
}

foreach (NetworkIdentity identity in nextSet)
{
if (!lastSet.Contains(identity))
{
InterestManager.ServerObjectManager.ShowToPlayer(identity, player);
}
}

// reset collections
lastSet.Clear();
foreach (NetworkIdentity identity in nextSet)
{
lastSet.Add(identity);
}

nextSet.Clear();
}
}

#region Overrides of NetworkVisibility

Expand All @@ -128,16 +60,19 @@ public override void OnSpawned(NetworkIdentity identity)
}

Vector3 a = identity.transform.position;
float sqRange = _sightDistnace * _sightDistnace;

foreach (INetworkPlayer player in InterestManager.ServerObjectManager.Server.Players)
{
Vector3 b = player.Identity.transform.position;

if (FastInDistanceXZ(a, b, sqRange))
{
InterestManager.ServerObjectManager.ShowToPlayer(identity, player);
}
if (!FastInDistanceXZ(a, b, _sightDistnace * _sightDistnace)) continue;

if (!VisibilitySystemData.ContainsKey(identity))
VisibilitySystemData.Add(identity, new HashSet<INetworkPlayer>());
else if (VisibilitySystemData.ContainsKey(identity) && !VisibilitySystemData[identity].Contains(player))
VisibilitySystemData[identity].Add(player);

InterestManager.ServerObjectManager.ShowToPlayer(identity, player);
}
}

Expand All @@ -151,16 +86,19 @@ public override void OnAuthenticated(INetworkPlayer player)
if (player.Identity == null) { return; }

Vector3 b = player.Identity.transform.position;
float sqRange = _sightDistnace * _sightDistnace;

foreach (NetworkIdentity identity in InterestManager.ServerObjectManager.Server.World.SpawnedIdentities)
{
Vector3 a = identity.transform.position;

if (FastInDistanceXZ(a, b, sqRange))
{
InterestManager.ServerObjectManager.ShowToPlayer(identity, player);
}
if (!FastInDistanceXZ(a, b, _sightDistnace * _sightDistnace)) continue;

if (!VisibilitySystemData.ContainsKey(identity))
VisibilitySystemData.Add(identity, new HashSet<INetworkPlayer>());
else if (VisibilitySystemData.ContainsKey(identity) && !VisibilitySystemData[identity].Contains(player))
VisibilitySystemData[identity].Add(player);

InterestManager.ServerObjectManager.ShowToPlayer(identity, player);
}
}

Expand All @@ -171,7 +109,27 @@ public override void CheckForObservers()
{
if (!(_nextUpdate < Time.time)) return;

Rebuild();
foreach (INetworkPlayer player in InterestManager.ServerObjectManager.Server.Players)
{
if(!VisibilitySystemData.ContainsKey(_identity)) continue;

VisibilitySystemData.TryGetValue(_identity, out HashSet<INetworkPlayer> players);

if (FastInDistanceXZ(player.Identity.transform.position, _identity.transform.position, _sightDistnace * _sightDistnace))
{
if (players != null && players.Contains(player)) continue;

VisibilitySystemData[_identity].Add(player);
InterestManager.ServerObjectManager.ShowToPlayer(_identity, player);
}
else
{
if(players !=null && !players.Contains(player)) continue;

VisibilitySystemData[_identity].Remove(player);
InterestManager.ServerObjectManager.HideToPlayer(_identity, player);
}
}

_nextUpdate += _updateInterval;
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
using System.Collections.Generic;
using Mirage.InterestManagement;
using Mirage.Logging;
using UnityEngine;
Expand All @@ -9,38 +10,12 @@ public class SceneVisibilityChecker : NetworkVisibility
{
static readonly ILogger logger = LogFactory.GetLogger<SceneVisibilityChecker>();

//public override bool OnCheckObserver(INetworkPlayer player)
//{
// NetworkIdentity character = player.Identity;
// if (character == null)
// {
// if (logger.LogEnabled()) logger.Log($"SceneChecker: {player} had no character");
// return false;
// }
#region Fields

// Scene playerScene = character.gameObject.scene;
// if (!playerScene.IsValid())
// {
// if (logger.WarnEnabled()) logger.LogWarning($"SceneChecker: Could not find scene for {player}");
// return false;
// }
private Scene _objectCurrentScene;
private NetworkIdentity Identity;

// Scene thisScene = gameObject.scene;
// bool visible = playerScene == thisScene;
// if (logger.LogEnabled()) logger.Log($"SceneChecker: {player} can see '{this}': {visible}");
// return visible;
//}

//public override void OnRebuildObservers(HashSet<INetworkPlayer> observers, bool initialize)
//{
// foreach (INetworkPlayer player in Server.Players)
// {
// if (OnCheckObserver(player))
// {
// observers.Add(player);
// }
// }
//}
#endregion

/// <summary>
/// Call this function on an object to move it to a new scene and rebuild its observers
Expand All @@ -65,17 +40,10 @@ public void MoveToScene(Scene scene)
// ServerObjectManager.SpawnVisibleObjects(Identity.Owner);
}

private void removeObservers(NetworkIdentity identity)
{
//HashSet<INetworkPlayer> observers = identity.observers;
//foreach (INetworkPlayer observer in observers)
//{
// observer.RemoveFromVisList(identity);
//}
}

public SceneVisibilityChecker(ServerObjectManager serverObjectManager) : base(serverObjectManager)
public SceneVisibilityChecker(ServerObjectManager serverObjectManager, Scene objectScene, NetworkIdentity identity) : base(serverObjectManager)
{
_objectCurrentScene = objectScene;
Identity = identity;
}

#region Overrides of NetworkVisibility
Expand All @@ -87,7 +55,7 @@ public SceneVisibilityChecker(ServerObjectManager serverObjectManager) : base(se
/// <param name="identity">The object just spawned</param>
public override void OnSpawned(NetworkIdentity identity)
{
throw new System.NotImplementedException();
// NOOP
}

/// <summary>
Expand All @@ -96,15 +64,14 @@ public override void OnSpawned(NetworkIdentity identity)
/// <param name="player"></param>
public override void OnAuthenticated(INetworkPlayer player)
{
throw new System.NotImplementedException();
if(player.Identity.gameObject.scene.handle != _objectCurrentScene.handle) return;
}

/// <summary>
///
/// </summary>
public override void CheckForObservers()
{
throw new System.NotImplementedException();
}

#endregion
Expand Down
14 changes: 9 additions & 5 deletions Assets/Mirage/Editor/NetworkInformationPreview.cs
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
using System.Collections.Generic;
using Mirage.InterestManagement;
using UnityEditor;
using UnityEngine;

Expand Down Expand Up @@ -172,7 +173,7 @@ float DrawNetworkBehaviors(NetworkIdentity identity, float initialX, float Y)

float DrawObservers(NetworkIdentity identity, float initialX, float Y)
{
if (identity.ServerObjectManager.InterestManager.Observers(identity).Count > 0)
if (identity.ServerObjectManager.InterestManager.ObserverSystems.Count > 0)
{
var observerRect = new Rect(initialX, Y + 10, 200, 20);

Expand All @@ -181,11 +182,14 @@ float DrawObservers(NetworkIdentity identity, float initialX, float Y)
observerRect.x += 20;
observerRect.y += observerRect.height;

foreach (INetworkPlayer player in identity.ServerObjectManager.InterestManager.Observers(identity))
foreach (ObserverData system in identity.ServerObjectManager.InterestManager.ObserverSystems)
{
GUI.Label(observerRect, player.Connection.EndPoint + ":" + player, styles.ComponentName);
observerRect.y += observerRect.height;
Y = observerRect.y;
foreach (INetworkPlayer player in system.Observers[identity])
{
GUI.Label(observerRect, player.Connection.EndPoint + ":" + player, styles.ComponentName);
observerRect.y += observerRect.height;
Y = observerRect.y;
}
}
}

Expand Down
23 changes: 9 additions & 14 deletions Assets/Mirage/Runtime/InterestManagement/InterestManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -144,7 +144,7 @@ protected internal void Send<T>(NetworkIdentity identity, T msg, int channelId =
{
OnSendProfilerMarker.Begin();

_observers = Observers(identity);
Observers(identity);

// remove skipped player. No need to send to them.
_observers.Remove(skip);
Expand Down Expand Up @@ -206,35 +206,30 @@ internal void UnRegisterVisibilitySystem(ref ObserverData system)
/// </summary>
/// <param name="identity">The identity of the object we want to check if player's can see it or not.</param>
/// <returns></returns>
internal List<INetworkPlayer> Observers(NetworkIdentity identity)
private void Observers(NetworkIdentity identity)
{
ObserverProfilerMarker.Begin();

_observers.Clear();

if (_visibilitySystems.Count == 0)
{
ObserverProfilerMarker.End();

return new List<INetworkPlayer>(ServerObjectManager.Server.Players);
_observers.AddRange(ServerObjectManager.Server.Players);
}

foreach (ObserverData visibilitySystem in _visibilitySystems)
{
foreach (KeyValuePair<INetworkPlayer, HashSet<NetworkIdentity>> observer in visibilitySystem.Observers)
{
if (!observer.Value.Contains(identity))
{
ObserverProfilerMarker.End();

return _observers;
}
if (!visibilitySystem.Observers.ContainsKey(identity)) continue;

_observers.AddRange(visibilitySystem.Observers.Keys);
foreach (KeyValuePair<NetworkIdentity, HashSet<INetworkPlayer>> observer in visibilitySystem.Observers)
{
_observers.AddRange(observer.Value);
}
}

ObserverProfilerMarker.End();

return _observers;
}

#endregion
Expand Down
4 changes: 2 additions & 2 deletions Assets/Mirage/Runtime/InterestManagement/NetworkVisibility.cs
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ public abstract class NetworkVisibility : INetworkVisibility

public InterestManager InterestManager => _serverObjectManager.InterestManager;

public Dictionary<INetworkPlayer, HashSet<NetworkIdentity>> VisibilitySystemData => _visibilitySystemData.Observers;
public Dictionary<NetworkIdentity, HashSet<INetworkPlayer>> VisibilitySystemData => _visibilitySystemData.Observers;

#endregion

Expand All @@ -26,7 +26,7 @@ protected NetworkVisibility(ServerObjectManager serverObjectManager)

public void Startup()
{
_visibilitySystemData = new ObserverData(this, new Dictionary<INetworkPlayer, HashSet<NetworkIdentity>>());
_visibilitySystemData = new ObserverData(this, new Dictionary<NetworkIdentity, HashSet<INetworkPlayer>>());

_serverObjectManager.InterestManager?.RegisterVisibilitySystem(ref _visibilitySystemData);
}
Expand Down
Loading

0 comments on commit a8e710c

Please sign in to comment.