diff --git a/Assets/FishNet/Runtime/Managing/Scened/LoadUnloadDatas/SceneLoadData.cs b/Assets/FishNet/Runtime/Managing/Scened/LoadUnloadDatas/SceneLoadData.cs
index 51c8cce4..7fcf33db 100644
--- a/Assets/FishNet/Runtime/Managing/Scened/LoadUnloadDatas/SceneLoadData.cs
+++ b/Assets/FishNet/Runtime/Managing/Scened/LoadUnloadDatas/SceneLoadData.cs
@@ -1,7 +1,7 @@
-using FishNet.Object;
-using FishNet.Serializing.Helping;
-using System.Collections.Generic;
+using System.Collections.Generic;
using System.IO;
+using FishNet.Object;
+using FishNet.Serializing.Helping;
using UnityEngine.SceneManagement;
namespace FishNet.Managing.Scened
@@ -50,13 +50,13 @@ public SceneLoadData(string sceneName) : this(new string[] { sceneName }, null)
///
///
/// Scene to load by handle.
- public SceneLoadData(int sceneHandle) : this(new int[] { sceneHandle }, null) { }
+ public SceneLoadData(ulong sceneHandle) : this(new[] { sceneHandle }, null) { }
///
///
/// Scene to load by handle.
/// Scene to load by name.
- public SceneLoadData(int sceneHandle, string sceneName) : this(new SceneLookupData(sceneHandle, sceneName)) { }
+ public SceneLoadData(ulong sceneHandle, string sceneName) : this(new SceneLookupData(sceneHandle, sceneName)) { }
///
///
@@ -76,7 +76,7 @@ public SceneLoadData(List sceneNames) : this(sceneNames.ToArray(), null)
///
///
/// Scenes to load by handle.
- public SceneLoadData(List sceneHandles) : this(sceneHandles.ToArray(), null) { }
+ public SceneLoadData(List sceneHandles) : this(sceneHandles.ToArray(), null) { }
///
///
@@ -91,7 +91,7 @@ public SceneLoadData(string[] sceneNames) : this(sceneNames, null) { }
///
///
/// Scenes to load by handle.
- public SceneLoadData(int[] sceneHandles) : this(sceneHandles, null) { }
+ public SceneLoadData(ulong[] sceneHandles) : this(sceneHandles, null) { }
///
///
@@ -132,7 +132,7 @@ public SceneLoadData(string[] sceneNames, NetworkObject[] movedNetworkObjects)
///
/// Scenes to load by handle.
/// NetworkObjects to move to the first specified scene.
- public SceneLoadData(int[] sceneHandles, NetworkObject[] movedNetworkObjects)
+ public SceneLoadData(ulong[] sceneHandles, NetworkObject[] movedNetworkObjects)
{
SceneLookupData[] datas = SceneLookupData.CreateData(sceneHandles);
Construct(datas, movedNetworkObjects);
diff --git a/Assets/FishNet/Runtime/Managing/Scened/LoadUnloadDatas/SceneUnloadData.cs b/Assets/FishNet/Runtime/Managing/Scened/LoadUnloadDatas/SceneUnloadData.cs
index 3e577dac..99641049 100644
--- a/Assets/FishNet/Runtime/Managing/Scened/LoadUnloadDatas/SceneUnloadData.cs
+++ b/Assets/FishNet/Runtime/Managing/Scened/LoadUnloadDatas/SceneUnloadData.cs
@@ -42,7 +42,7 @@ public SceneUnloadData(string sceneName) : this(new string[] { sceneName }) { }
///
///
/// Scene to unload by handle.
- public SceneUnloadData(int sceneHandle) : this(new int[] { sceneHandle }) { }
+ public SceneUnloadData(ulong sceneHandle) : this(new[] { sceneHandle }) { }
///
///
@@ -65,7 +65,7 @@ public SceneUnloadData(List sceneNames) : this(sceneNames.ToArray()) { }
///
///
/// Scenes to unload by handles.
- public SceneUnloadData(List sceneHandles) : this(sceneHandles.ToArray()) { }
+ public SceneUnloadData(List sceneHandles) : this(sceneHandles.ToArray()) { }
///
///
@@ -86,7 +86,7 @@ public SceneUnloadData(string[] sceneNames)
///
///
/// Scenes to unload by handles.
- public SceneUnloadData(int[] sceneHandles)
+ public SceneUnloadData(ulong[] sceneHandles)
{
SceneLookupDatas = SceneLookupData.CreateData(sceneHandles);
}
diff --git a/Assets/FishNet/Runtime/Managing/Scened/SceneHandleExtensions.cs b/Assets/FishNet/Runtime/Managing/Scened/SceneHandleExtensions.cs
new file mode 100644
index 00000000..e0e2f437
--- /dev/null
+++ b/Assets/FishNet/Runtime/Managing/Scened/SceneHandleExtensions.cs
@@ -0,0 +1,23 @@
+using UnityEngine.SceneManagement;
+
+namespace FishNet.Managing.Scened
+{
+ internal static class SceneHandleExtensions
+ {
+ ///
+ /// Returns the raw handle identifier of a scene as a ulong.
+ ///
+ ///
+ /// Unity 6000.5+ changed Scene.handle to an EntityId struct exposing GetRawData().
+ /// Earlier versions expose handle as an int.
+ ///
+ public static ulong GetHandleId(this Scene s)
+ {
+#if UNITY_6000_5_OR_NEWER
+ return s.handle.GetRawData();
+#else
+ return (ulong)(uint)s.handle;
+#endif
+ }
+ }
+}
diff --git a/Assets/FishNet/Runtime/Managing/Scened/SceneLookupData.cs b/Assets/FishNet/Runtime/Managing/Scened/SceneLookupData.cs
index 6e3a4554..6e65d686 100644
--- a/Assets/FishNet/Runtime/Managing/Scened/SceneLookupData.cs
+++ b/Assets/FishNet/Runtime/Managing/Scened/SceneLookupData.cs
@@ -1,6 +1,6 @@
-using GameKit.Dependencies.Utilities;
-using System;
+using System;
using System.Collections.Generic;
+using GameKit.Dependencies.Utilities;
using UnityEngine.SceneManagement;
namespace FishNet.Managing.Scened
@@ -24,7 +24,7 @@ public static string[] GetNames(this SceneLookupData[] datas)
return names;
}
-
+
///
/// Returns Names from SceneLookupData.
///
@@ -48,7 +48,7 @@ public class SceneLookupData : IEquatable
///
/// Handle of the scene. If value is 0, then handle is not used.
///
- public int Handle;
+ public ulong Handle;
///
/// Name of the scene.
///
@@ -62,7 +62,7 @@ public string NameOnly
{
if (string.IsNullOrEmpty(Name))
return string.Empty;
-
+
string name = System.IO.Path.GetFileName(Name);
return RemoveUnityExtension(name);
}
@@ -89,7 +89,7 @@ public SceneLookupData() { }
/// Scene to generate from.
public SceneLookupData(Scene scene)
{
- Handle = scene.handle;
+ Handle = scene.GetHandleId();
Name = scene.name;
}
@@ -104,7 +104,7 @@ public SceneLookupData(string name)
///
///
/// Scene handle to generate from.
- public SceneLookupData(int handle)
+ public SceneLookupData(ulong handle)
{
Handle = handle;
}
@@ -113,7 +113,7 @@ public SceneLookupData(int handle)
///
/// Scene handle to generate from.
/// Name to generate from if handle is 0.
- public SceneLookupData(int handle, string name)
+ public SceneLookupData(ulong handle, string name)
{
Handle = handle;
Name = name;
@@ -212,7 +212,7 @@ public override string ToString()
///
/// Scene handle to create from.
///
- public static SceneLookupData CreateData(int handle) => new(handle);
+ public static SceneLookupData CreateData(ulong handle) => new(handle);
///
/// Returns a SceneLookupData collection.
@@ -233,7 +233,7 @@ public override string ToString()
///
/// Scene handles to create from.
///
- public static SceneLookupData[] CreateData(List handles) => CreateData(handles.ToArray());
+ public static SceneLookupData[] CreateData(List handles) => CreateData(handles.ToArray());
///
/// Returns a SceneLookupData collection.
@@ -345,11 +345,11 @@ public static SceneLookupData[] ValidateData(SceneLookupData[] datas)
///
/// Scene handles to create from.
///
- public static SceneLookupData[] CreateData(int[] handles)
+ public static SceneLookupData[] CreateData(ulong[] handles)
{
bool invalidFound = false;
List result = new();
- foreach (int item in handles)
+ foreach (var item in handles)
{
if (item == 0)
{
@@ -402,7 +402,7 @@ public Scene GetScene(out bool foundByHandle, bool warnIfDuplicates = true)
if (Handle != 0)
{
result = SceneManager.GetScene(Handle);
- if (result.handle != 0)
+ if (result.GetHandleId() != 0)
foundByHandle = true;
}
diff --git a/Assets/FishNet/Runtime/Managing/Scened/SceneManager.cs b/Assets/FishNet/Runtime/Managing/Scened/SceneManager.cs
index 6bae7b5c..165e02d9 100644
--- a/Assets/FishNet/Runtime/Managing/Scened/SceneManager.cs
+++ b/Assets/FishNet/Runtime/Managing/Scened/SceneManager.cs
@@ -1,4 +1,8 @@
-using FishNet.Connection;
+using System;
+using System.Collections;
+using System.Collections.Generic;
+using System.Linq;
+using FishNet.Connection;
using FishNet.Managing.Client;
using FishNet.Managing.Logging;
using FishNet.Managing.Server;
@@ -7,10 +11,6 @@
using FishNet.Transporting;
using GameKit.Dependencies.Utilities;
using GameKit.Dependencies.Utilities.Types;
-using System;
-using System.Collections;
-using System.Collections.Generic;
-using System.Linq;
using UnityEngine;
using UnityEngine.SceneManagement;
using UnityEngine.Serialization;
@@ -34,11 +34,11 @@ public class PendingClientSceneLoads
///
/// Scene handles which have clients that have not yet confirmed the loading status.
///
- private Dictionary> _scenesWithPendingLoads = new();
+ private Dictionary> _scenesWithPendingLoads = new();
///
/// Clients with pending loads, and each scene handle pending.
///
- private Dictionary> _clientsWithPendingLoads = new();
+ private Dictionary> _clientsWithPendingLoads = new();
///
/// Clients which have been sent the initial scene load with no scenes specified.
///
@@ -49,11 +49,11 @@ public class PendingClientSceneLoads
///
/// Adds a pending load for a client.
///
- public void AddClientToScene(NetworkConnection connection, int sceneHandle)
+ public void AddClientToScene(NetworkConnection connection, ulong sceneHandle)
{
/* The client has 1 or more pending loads already. See
* if the specified scene is already pending. */
- if (_clientsWithPendingLoads.TryGetValueIL2CPP(connection, out List sceneList))
+ if (_clientsWithPendingLoads.TryGetValueIL2CPP(connection, out List sceneList))
{
//Scene is already marked for the connection.
if (sceneList.Contains(sceneHandle))
@@ -81,14 +81,14 @@ public void AddClientToScene(NetworkConnection connection, int sceneHandle)
/// Removes a client from all pending loads.
/// Scene handles which no longer have clients pending loads.
- internal List RemoveClientFromAllScenes(NetworkConnection conn)
+ internal List RemoveClientFromAllScenes(NetworkConnection conn)
{
- List emptyScenes = new();
+ List emptyScenes = new();
- if (!_clientsWithPendingLoads.TryGetValueIL2CPP(conn, out List sceneList))
+ if (!_clientsWithPendingLoads.TryGetValueIL2CPP(conn, out List sceneList))
return emptyScenes;
- foreach (int sceneHandle in sceneList)
+ foreach (var sceneHandle in sceneList)
{
/* If the scene is in the clients list then it should
* be in scenesWithPendingLoads. This is a safety check but
@@ -113,7 +113,7 @@ internal List RemoveClientFromAllScenes(NetworkConnection conn)
/// Becomes true if the scene which the connection is being removed from has no more pending loads.
/// True if the client had the specified scene as pending.
- internal bool RemoveClientFromScene(NetworkConnection conn, int sceneHandle, out bool sceneHasNoPendingLoads)
+ internal bool RemoveClientFromScene(NetworkConnection conn, ulong sceneHandle, out bool sceneHasNoPendingLoads)
{
// The scene has does not have any pending clients.
if (!_scenesWithPendingLoads.TryGetValueIL2CPP(sceneHandle, out HashSet connectionsLoadingScene))
@@ -136,7 +136,7 @@ internal bool RemoveClientFromScene(NetworkConnection conn, int sceneHandle, out
/* If client does not have any pending loads then
* there is nothing to remove, which means the requested
* scene still has clients in it. */
- if (!_clientsWithPendingLoads.TryGetValueIL2CPP(conn, out List sceneList))
+ if (!_clientsWithPendingLoads.TryGetValueIL2CPP(conn, out List sceneList))
{
sceneHasNoPendingLoads = false;
return false;
@@ -176,7 +176,7 @@ internal bool RemoveClientFromScene(NetworkConnection conn, int sceneHandle, out
///
/// Returns if a scene has any number of clients still pending load.
///
- internal bool HasSceneAnyPendingLoads(int sceneHandle) => _scenesWithPendingLoads.TryGetValueIL2CPP(sceneHandle, out _);
+ internal bool HasSceneAnyPendingLoads(ulong sceneHandle) => _scenesWithPendingLoads.TryGetValueIL2CPP(sceneHandle, out _);
///
/// Clears all information.
@@ -635,7 +635,7 @@ private void ClientDisconnected(NetworkConnection conn)
/* True if SceneConnections has no more connections
* in its scene, as well if the scene checked is in
* has no other clients pending load confirmation. */
- bool isSceneNowEmpty = removed && hs.Count == 0 && !_pendingClientSceneLoads.HasSceneAnyPendingLoads(scene.handle);
+ bool isSceneNowEmpty = removed && hs.Count == 0 && !_pendingClientSceneLoads.HasSceneAnyPendingLoads(scene.GetHandleId());
//True if not a global scene and not in scenes to be manually unloaded.
bool notGlobalAndNotManualUnload = !IsGlobalScene(scene) && !_manualUnloadScenes.Contains(scene);
@@ -1058,7 +1058,7 @@ private IEnumerator __LoadScenes()
/* Scene queue data scenes.
* All scenes in the scene queue data whether they will be loaded or not. */
List requestedLoadSceneNames = new();
- List requestedLoadSceneHandles = new();
+ List requestedLoadSceneHandles = new();
/* Make a null filled array. This will be populated
* using loaded scenes, or already loaded (eg cannot be loaded) scenes. */
@@ -1081,7 +1081,7 @@ private IEnumerator __LoadScenes()
{
requestedLoadSceneNames.Add(s.name);
if (byHandle)
- requestedLoadSceneHandles.Add(s.handle);
+ requestedLoadSceneHandles.Add(s.GetHandleId());
}
if (CanLoadScene(data, lookupData))
@@ -1124,7 +1124,7 @@ private IEnumerator __LoadScenes()
}
// Connection scenes handles prior to ConnectionScenes being modified.
- List connectionScenesHandlesCached = new();
+ List connectionScenesHandlesCached = new();
// If replacing scenes.
if (replaceScenes != ReplaceOption.None)
{
@@ -1137,7 +1137,7 @@ private IEnumerator __LoadScenes()
{
Scene[] sceneConnectionsKeys = SceneConnections.Keys.ToArray();
for (int i = 0; i < sceneConnectionsKeys.Length; i++)
- connectionScenesHandlesCached.Add(sceneConnectionsKeys[i].handle);
+ connectionScenesHandlesCached.Add(sceneConnectionsKeys[i].GetHandleId());
// If global then remove all connections from all scenes.
if (data.ScopeType == SceneScopeType.Global)
@@ -1155,7 +1155,7 @@ private IEnumerator __LoadScenes()
else
{
foreach (Scene s in NetworkManager.ClientManager.Connection.Scenes)
- connectionScenesHandlesCached.Add(s.handle);
+ connectionScenesHandlesCached.Add(s.GetHandleId());
}
}
@@ -1181,7 +1181,7 @@ private IEnumerator __LoadScenes()
if (requestedLoadSceneNames.Contains(s.name))
continue;
// Same as above but using handles.
- if (requestedLoadSceneHandles.Contains(s.handle))
+ if (requestedLoadSceneHandles.Contains(s.GetHandleId()))
continue;
/* Cannot unload global scenes. If
* replace scenes was used for a global
@@ -1193,7 +1193,7 @@ private IEnumerator __LoadScenes()
if (_manualUnloadScenes.Contains(s))
continue;
- bool inScenesCache = connectionScenesHandlesCached.Contains(s.handle);
+ bool inScenesCache = connectionScenesHandlesCached.Contains(s.GetHandleId());
HashSet conns;
bool inScenesCurrent = SceneConnections.ContainsKey(s);
// If was in scenes previously but isnt now then no connections reside in the scene.
@@ -2245,13 +2245,13 @@ public static Scene GetScene(string sceneName, NetworkManager nm = null, bool wa
///
///
///
- public static Scene GetScene(int sceneHandle)
+ public static Scene GetScene(ulong sceneHandle)
{
int count = UnitySceneManager.sceneCount;
for (int i = 0; i < count; i++)
{
Scene s = UnitySceneManager.GetSceneAt(i);
- if (s.handle == sceneHandle)
+ if (s.GetHandleId() == sceneHandle)
return s;
}
@@ -2354,7 +2354,7 @@ private void RemoveOccupiedScenes(List scenes)
{
Scene s = scenes[i];
- if (SceneConnections.TryGetValueIL2CPP(s, out _) || _pendingClientSceneLoads.HasSceneAnyPendingLoads(s.handle))
+ if (SceneConnections.TryGetValueIL2CPP(s, out _) || _pendingClientSceneLoads.HasSceneAnyPendingLoads(s.GetHandleId()))
{
scenes.RemoveAt(i);
i--;
@@ -2365,7 +2365,7 @@ private void RemoveOccupiedScenes(List scenes)
///
/// Adds a pending load for a connection.
///
- private void AddPendingLoad(NetworkConnection[] conns, int sceneHandle)
+ private void AddPendingLoad(NetworkConnection[] conns, ulong sceneHandle)
{
foreach (NetworkConnection c in conns)
{
diff --git a/Assets/FishNet/Runtime/Managing/Scened/UnloadedScene.cs b/Assets/FishNet/Runtime/Managing/Scened/UnloadedScene.cs
index 5f89fb49..6e21c8c6 100644
--- a/Assets/FishNet/Runtime/Managing/Scened/UnloadedScene.cs
+++ b/Assets/FishNet/Runtime/Managing/Scened/UnloadedScene.cs
@@ -5,15 +5,15 @@ namespace FishNet.Managing.Scened
public struct UnloadedScene
{
public readonly string Name;
- public readonly int Handle;
+ public readonly ulong Handle;
public UnloadedScene(Scene s)
{
Name = s.name;
- Handle = s.handle;
+ Handle = s.GetHandleId();
}
- public UnloadedScene(string name, int handle)
+ public UnloadedScene(string name, ulong handle)
{
Name = name;
Handle = handle;
@@ -30,7 +30,7 @@ public Scene GetScene()
for (int i = 0; i < loadedScenes; i++)
{
Scene s = UnityEngine.SceneManagement.SceneManager.GetSceneAt(i);
- if (s.IsValid() && s.handle == Handle)
+ if (s.IsValid() && s.GetHandleId() == Handle)
return s;
}
diff --git a/Assets/FishNet/Runtime/Observing/NetworkObserver.cs b/Assets/FishNet/Runtime/Observing/NetworkObserver.cs
index fd0fb35d..7b80f7fc 100644
--- a/Assets/FishNet/Runtime/Observing/NetworkObserver.cs
+++ b/Assets/FishNet/Runtime/Observing/NetworkObserver.cs
@@ -1,11 +1,11 @@
-using FishNet.Connection;
+using System.Collections.Generic;
+using FishNet.Connection;
using FishNet.Documenting;
+using FishNet.Managing;
using FishNet.Managing.Server;
using FishNet.Object;
using FishNet.Transporting;
using GameKit.Dependencies.Utilities;
-using System.Collections.Generic;
-using FishNet.Managing;
using UnityEngine;
namespace FishNet.Observing
@@ -155,11 +155,18 @@ internal void Deinitialize(bool destroyed)
foreach (ObserverCondition item in _observerConditions)
{
item.Deinitialize(destroyed);
- /* Use GetInstanceId to ensure the object is actually
- * instantiated. If Id is negative, then it's instantiated
- * and not a reference to the original object. */
+ /* Conditions are always Instantiate() clones at this point
+ * (see Initialize), so destroying any valid entry only ever
+ * destroys the clone, never the source asset.
+ * On 6000.5+ use the EntityId API: GetInstanceID()/`< 0`
+ * route through the obsolete EntityId<->int conversion (CS0618). */
+#if UNITY_6000_5_OR_NEWER
+ if (destroyed && item.GetEntityId().IsValid())
+ Destroy(item);
+#else
if (destroyed && item.GetInstanceID() < 0)
Destroy(item);
+#endif
}
// Clean up lists.
@@ -309,10 +316,10 @@ internal ObserverStateChange RebuildObservers(NetworkConnection connection, bool
if (!_initialized)
{
string goName = gameObject == null ? "Empty" : gameObject.name;
-
+
NetworkManager nm = _networkObject == null ? null : _networkObject.NetworkManager;
nm.LogError($"{GetType().Name} is not initialized on NetworkObject [{goName}]. RebuildObservers should not be called. If you are able to reproduce this error consistently please report this issue.");
-
+
return ObserverStateChange.Unchanged;
}
diff --git a/Assets/FishNet/Runtime/Plugins/GameKit/Dependencies/Utilities/Dictionaries.cs b/Assets/FishNet/Runtime/Plugins/GameKit/Dependencies/Utilities/Dictionaries.cs
index cd5c03ca..2678c26e 100644
--- a/Assets/FishNet/Runtime/Plugins/GameKit/Dependencies/Utilities/Dictionaries.cs
+++ b/Assets/FishNet/Runtime/Plugins/GameKit/Dependencies/Utilities/Dictionaries.cs
@@ -11,7 +11,7 @@ public static class DictionaryFN
///
public static bool TryGetValueIL2CPP(this IReadOnlyDictionary dict, TKey key, out TValue value)
{
- #if ENABLE_IL2CPP && UNITY_IOS || UNITY_ANDROID
+#if ENABLE_IL2CPP && UNITY_IOS || UNITY_ANDROID
if (dict.ContainsKey(key))
{
value = dict[key];
@@ -20,12 +20,12 @@ public static bool TryGetValueIL2CPP(this IReadOnlyDictionary
/// Returns values as a list.
///
diff --git a/Assets/FishNet/Runtime/Serializing/Helping/Comparers.cs b/Assets/FishNet/Runtime/Serializing/Helping/Comparers.cs
index f294ae66..98cb2ac5 100644
--- a/Assets/FishNet/Runtime/Serializing/Helping/Comparers.cs
+++ b/Assets/FishNet/Runtime/Serializing/Helping/Comparers.cs
@@ -1,5 +1,6 @@
using System;
using System.Collections.Generic;
+using FishNet.Managing.Scened;
using UnityEngine.SceneManagement;
namespace FishNet.Serializing.Helping
@@ -48,7 +49,7 @@ public bool Equals(Scene a, Scene b)
if (!a.IsValid() || !b.IsValid())
return false;
- if (a.handle != 0 || b.handle != 0)
+ if (a.GetHandleId() != 0 || b.GetHandleId() != 0)
return a.handle == b.handle;
return a.name == b.name;
diff --git a/Assets/FishNet/Runtime/Serializing/SceneComparer.cs b/Assets/FishNet/Runtime/Serializing/SceneComparer.cs
index d4a4e076..9181469a 100644
--- a/Assets/FishNet/Runtime/Serializing/SceneComparer.cs
+++ b/Assets/FishNet/Runtime/Serializing/SceneComparer.cs
@@ -12,7 +12,7 @@ public override bool Equals(Scene a, Scene b)
public override int GetHashCode(Scene obj)
{
- return obj.handle;
+ return obj.handle.GetHashCode();
}
}
}
\ No newline at end of file