quantum-space-buddies/QuantumUNET/QSBNetworkScene.cs

278 lines
7.1 KiB
C#
Raw Normal View History

2020-12-07 21:19:16 +00:00
using QuantumUNET.Components;
using System.Collections.Generic;
2020-12-02 12:42:26 +00:00
using UnityEngine;
using UnityEngine.Networking;
2020-12-04 22:14:53 +00:00
namespace QuantumUNET
2020-12-02 12:42:26 +00:00
{
2020-12-03 08:28:05 +00:00
internal class QSBNetworkScene
2020-12-02 12:42:26 +00:00
{
2020-12-16 08:45:58 +00:00
internal static Dictionary<NetworkHash128, GameObject> guidToPrefab { get; } = new Dictionary<NetworkHash128, GameObject>();
2020-12-02 12:42:26 +00:00
internal static Dictionary<NetworkHash128, QSBSpawnDelegate> spawnHandlers { get; } = new Dictionary<NetworkHash128, QSBSpawnDelegate>();
2020-12-02 12:42:26 +00:00
2020-12-16 08:45:58 +00:00
internal static Dictionary<NetworkHash128, UnSpawnDelegate> unspawnHandlers { get; } = new Dictionary<NetworkHash128, UnSpawnDelegate>();
2020-12-02 12:42:26 +00:00
internal Dictionary<NetworkInstanceId, QSBNetworkIdentity> localObjects { get; } = new Dictionary<NetworkInstanceId, QSBNetworkIdentity>();
2020-12-02 20:43:16 +00:00
2020-12-02 12:42:26 +00:00
internal void Shutdown()
{
2020-12-07 21:04:52 +00:00
ClearLocalObjects();
2020-12-02 12:42:26 +00:00
ClearSpawners();
}
2020-12-16 08:57:15 +00:00
internal void SetLocalObject(NetworkInstanceId netId, GameObject obj, bool isClient, bool isServer)
2020-12-02 12:42:26 +00:00
{
if (obj == null)
{
2020-12-07 21:04:52 +00:00
localObjects[netId] = null;
2020-12-02 12:42:26 +00:00
}
else
{
QSBNetworkIdentity networkIdentity = null;
2020-12-07 21:04:52 +00:00
if (localObjects.ContainsKey(netId))
2020-12-02 12:42:26 +00:00
{
2020-12-07 21:04:52 +00:00
networkIdentity = localObjects[netId];
2020-12-02 12:42:26 +00:00
}
if (networkIdentity == null)
{
networkIdentity = obj.GetComponent<QSBNetworkIdentity>();
2020-12-07 21:04:52 +00:00
localObjects[netId] = networkIdentity;
2020-12-02 12:42:26 +00:00
}
networkIdentity.UpdateClientServer(isClient, isServer);
}
}
2020-12-16 08:57:15 +00:00
internal GameObject FindLocalObject(NetworkInstanceId netId)
2020-12-02 12:42:26 +00:00
{
2020-12-07 21:04:52 +00:00
if (localObjects.ContainsKey(netId))
2020-12-02 12:42:26 +00:00
{
2020-12-07 21:04:52 +00:00
var networkIdentity = localObjects[netId];
2020-12-02 12:42:26 +00:00
if (networkIdentity != null)
{
return networkIdentity.gameObject;
}
}
return null;
}
2020-12-16 08:57:15 +00:00
internal bool GetNetworkIdentity(NetworkInstanceId netId, out QSBNetworkIdentity uv)
2020-12-02 12:42:26 +00:00
{
bool result;
2020-12-02 20:43:16 +00:00
if (localObjects.ContainsKey(netId) && localObjects[netId] != null)
2020-12-02 12:42:26 +00:00
{
2020-12-02 20:43:16 +00:00
uv = localObjects[netId];
2020-12-02 12:42:26 +00:00
result = true;
}
else
{
uv = null;
result = false;
}
return result;
}
2020-12-16 08:57:15 +00:00
internal bool RemoveLocalObject(NetworkInstanceId netId) => localObjects.Remove(netId);
2020-12-02 12:42:26 +00:00
2020-12-16 08:57:15 +00:00
internal bool RemoveLocalObjectAndDestroy(NetworkInstanceId netId)
2020-12-02 12:42:26 +00:00
{
bool result;
2020-12-07 21:04:52 +00:00
if (localObjects.ContainsKey(netId))
2020-12-02 12:42:26 +00:00
{
2020-12-07 21:04:52 +00:00
var networkIdentity = localObjects[netId];
Object.Destroy(networkIdentity.gameObject);
2020-12-07 21:04:52 +00:00
result = localObjects.Remove(netId);
2020-12-02 12:42:26 +00:00
}
else
{
result = false;
}
return result;
}
internal void ClearLocalObjects() => localObjects.Clear();
2020-12-02 12:42:26 +00:00
2020-12-16 08:45:58 +00:00
internal static void RegisterPrefab(GameObject prefab, NetworkHash128 newAssetId)
2020-12-02 12:42:26 +00:00
{
2020-12-07 21:04:52 +00:00
var component = prefab.GetComponent<QSBNetworkIdentity>();
2020-12-02 12:42:26 +00:00
if (component)
{
component.SetDynamicAssetId(newAssetId);
guidToPrefab[component.AssetId] = prefab;
}
2020-12-18 20:20:54 +00:00
else
2020-12-02 12:42:26 +00:00
{
Debug.LogError($"Could not register '{prefab.name}' since it contains no NetworkIdentity component");
2020-12-02 12:42:26 +00:00
}
}
internal static void RegisterPrefab(GameObject prefab)
{
2020-12-07 21:04:52 +00:00
var component = prefab.GetComponent<QSBNetworkIdentity>();
2020-12-02 12:42:26 +00:00
if (component)
{
2020-12-02 20:43:16 +00:00
guidToPrefab[component.AssetId] = prefab;
2020-12-07 21:04:52 +00:00
var componentsInChildren = prefab.GetComponentsInChildren<NetworkIdentity>();
2020-12-02 12:42:26 +00:00
if (componentsInChildren.Length > 1)
{
Debug.LogWarning(
$"The prefab '{prefab.name}' has multiple NetworkIdentity components. There can only be one NetworkIdentity on a prefab, and it must be on the root object.");
2020-12-02 12:42:26 +00:00
}
}
2020-12-18 20:20:54 +00:00
else
2020-12-02 12:42:26 +00:00
{
Debug.LogError($"Could not register '{prefab.name}' since it contains no NetworkIdentity component");
2020-12-02 12:42:26 +00:00
}
}
2020-12-16 08:45:58 +00:00
internal static bool GetPrefab(NetworkHash128 assetId, out GameObject prefab)
2020-12-02 12:42:26 +00:00
{
bool result;
if (!assetId.IsValid())
{
prefab = null;
result = false;
}
else if (guidToPrefab.ContainsKey(assetId) && guidToPrefab[assetId] != null)
{
prefab = guidToPrefab[assetId];
result = true;
}
else
{
prefab = null;
result = false;
}
return result;
}
internal static void ClearSpawners()
{
guidToPrefab.Clear();
spawnHandlers.Clear();
unspawnHandlers.Clear();
}
2020-12-16 08:45:58 +00:00
public static void UnregisterSpawnHandler(NetworkHash128 assetId)
2020-12-02 12:42:26 +00:00
{
spawnHandlers.Remove(assetId);
unspawnHandlers.Remove(assetId);
}
internal static void RegisterSpawnHandler(NetworkHash128 assetId, QSBSpawnDelegate spawnHandler, UnSpawnDelegate unspawnHandler)
2020-12-02 12:42:26 +00:00
{
if (spawnHandler == null || unspawnHandler == null)
{
Debug.LogError($"RegisterSpawnHandler custom spawn function null for {assetId}");
2020-12-02 12:42:26 +00:00
}
else
{
spawnHandlers[assetId] = spawnHandler;
unspawnHandlers[assetId] = unspawnHandler;
}
}
internal static void UnregisterPrefab(GameObject prefab)
{
2020-12-07 21:04:52 +00:00
var component = prefab.GetComponent<QSBNetworkIdentity>();
2020-12-02 12:42:26 +00:00
if (component == null)
{
Debug.LogError($"Could not unregister '{prefab.name}' since it contains no NetworkIdentity component");
2020-12-02 12:42:26 +00:00
}
else
{
2020-12-02 20:43:16 +00:00
spawnHandlers.Remove(component.AssetId);
unspawnHandlers.Remove(component.AssetId);
2020-12-02 12:42:26 +00:00
}
}
internal static void RegisterPrefab(GameObject prefab, QSBSpawnDelegate spawnHandler, UnSpawnDelegate unspawnHandler)
2020-12-02 12:42:26 +00:00
{
2020-12-07 21:04:52 +00:00
var component = prefab.GetComponent<QSBNetworkIdentity>();
2020-12-02 12:42:26 +00:00
if (component == null)
{
Debug.LogError($"Could not register '{prefab.name}' since it contains no NetworkIdentity component");
2020-12-02 12:42:26 +00:00
}
else if (spawnHandler == null || unspawnHandler == null)
{
Debug.LogError($"RegisterPrefab custom spawn function null for {component.AssetId}");
2020-12-02 12:42:26 +00:00
}
2020-12-02 20:43:16 +00:00
else if (!component.AssetId.IsValid())
2020-12-02 12:42:26 +00:00
{
Debug.LogError($"RegisterPrefab game object {prefab.name} has no prefab. Use RegisterSpawnHandler() instead?");
2020-12-02 12:42:26 +00:00
}
else
{
2020-12-02 20:43:16 +00:00
spawnHandlers[component.AssetId] = spawnHandler;
unspawnHandlers[component.AssetId] = unspawnHandler;
2020-12-02 12:42:26 +00:00
}
}
internal static bool GetSpawnHandler(NetworkHash128 assetId, out QSBSpawnDelegate handler)
2020-12-02 12:42:26 +00:00
{
bool result;
if (spawnHandlers.ContainsKey(assetId))
{
handler = spawnHandlers[assetId];
result = true;
}
else
{
handler = null;
result = false;
}
return result;
}
2020-12-16 08:45:58 +00:00
internal static bool InvokeUnSpawnHandler(NetworkHash128 assetId, GameObject obj)
2020-12-02 12:42:26 +00:00
{
bool result;
if (unspawnHandlers.ContainsKey(assetId) && unspawnHandlers[assetId] != null)
{
2020-12-07 21:04:52 +00:00
var unSpawnDelegate = unspawnHandlers[assetId];
2020-12-02 12:42:26 +00:00
unSpawnDelegate(obj);
result = true;
}
else
{
result = false;
}
return result;
}
internal void DestroyAllClientObjects()
{
2020-12-07 21:04:52 +00:00
foreach (var key in localObjects.Keys)
2020-12-02 12:42:26 +00:00
{
2020-12-07 21:04:52 +00:00
var networkIdentity = localObjects[key];
2020-12-02 12:42:26 +00:00
if (networkIdentity != null && networkIdentity.gameObject != null)
{
if (!InvokeUnSpawnHandler(networkIdentity.AssetId, networkIdentity.gameObject))
{
if (networkIdentity.SceneId.IsEmpty())
{
Object.Destroy(networkIdentity.gameObject);
2020-12-02 12:42:26 +00:00
}
else
{
networkIdentity.MarkForReset();
networkIdentity.gameObject.SetActive(false);
}
}
}
}
2020-12-07 21:04:52 +00:00
ClearLocalObjects();
2020-12-02 12:42:26 +00:00
}
internal void DumpAllClientObjects()
{
2020-12-07 21:04:52 +00:00
foreach (var networkInstanceId in localObjects.Keys)
2020-12-02 12:42:26 +00:00
{
2020-12-07 21:04:52 +00:00
var networkIdentity = localObjects[networkInstanceId];
Debug.Log(networkIdentity != null
? $"ID:{networkInstanceId} OBJ:{networkIdentity.gameObject} AS:{networkIdentity.AssetId}"
: $"ID:{networkInstanceId} OBJ: null");
2020-12-02 12:42:26 +00:00
}
}
}
}