online game working
This commit is contained in:
@@ -94,6 +94,8 @@ namespace MegaKoop.Game.Networking
|
|||||||
IsLocal = true
|
IsLocal = true
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pendingPlayers.Sort((a, b) => string.CompareOrdinal(a.SteamId ?? string.Empty, b.SteamId ?? string.Empty));
|
||||||
}
|
}
|
||||||
|
|
||||||
private void HandleSceneLoaded(Scene scene, LoadSceneMode mode)
|
private void HandleSceneLoaded(Scene scene, LoadSceneMode mode)
|
||||||
@@ -147,7 +149,7 @@ namespace MegaKoop.Game.Networking
|
|||||||
var clone = Instantiate(template, spawnPosition, baseRotation, parent);
|
var clone = Instantiate(template, spawnPosition, baseRotation, parent);
|
||||||
clone.name = BuildPlayerName(info, i);
|
clone.name = BuildPlayerName(info, i);
|
||||||
|
|
||||||
ConfigureCloneForPlayer(clone, info);
|
ConfigureCloneForPlayer(clone, info, i);
|
||||||
|
|
||||||
clone.SetActive(true);
|
clone.SetActive(true);
|
||||||
}
|
}
|
||||||
@@ -184,13 +186,17 @@ namespace MegaKoop.Game.Networking
|
|||||||
return center + offset;
|
return center + offset;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void ConfigureCloneForPlayer(GameObject clone, LobbyPlayerInfo info)
|
private void ConfigureCloneForPlayer(GameObject clone, LobbyPlayerInfo info, int index)
|
||||||
{
|
{
|
||||||
var controller = clone.GetComponent<ThirdPersonCharacterController>();
|
// Ensure network identity is deterministic across clients.
|
||||||
if (controller != null)
|
var identity = clone.GetComponent<NetworkIdentity>() ?? clone.AddComponent<NetworkIdentity>();
|
||||||
{
|
identity.SetNetworkId(index + 1);
|
||||||
controller.enabled = info.IsLocal;
|
|
||||||
}
|
var bridge = clone.GetComponent<SteamCharacterNetworkBridge>() ?? clone.AddComponent<SteamCharacterNetworkBridge>();
|
||||||
|
bridge.AssignOwner(ParseSteamId(info.SteamId), info.IsLocal);
|
||||||
|
|
||||||
|
var inputSender = clone.GetComponent<SteamLocalInputSender>() ?? clone.AddComponent<SteamLocalInputSender>();
|
||||||
|
inputSender.enabled = info.IsLocal;
|
||||||
|
|
||||||
// Local player keeps the camera and audio; remote avatars are visual only.
|
// Local player keeps the camera and audio; remote avatars are visual only.
|
||||||
var cameras = clone.GetComponentsInChildren<Camera>(true);
|
var cameras = clone.GetComponentsInChildren<Camera>(true);
|
||||||
@@ -217,11 +223,8 @@ namespace MegaKoop.Game.Networking
|
|||||||
if (thirdPersonCamera != null)
|
if (thirdPersonCamera != null)
|
||||||
{
|
{
|
||||||
thirdPersonCamera.enabled = info.IsLocal;
|
thirdPersonCamera.enabled = info.IsLocal;
|
||||||
if (info.IsLocal)
|
|
||||||
{
|
|
||||||
thirdPersonCamera.SetTarget(clone.transform);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private static string BuildPlayerName(LobbyPlayerInfo info, int index)
|
private static string BuildPlayerName(LobbyPlayerInfo info, int index)
|
||||||
@@ -241,6 +244,21 @@ namespace MegaKoop.Game.Networking
|
|||||||
return "You";
|
return "You";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static ulong ParseSteamId(string steamId)
|
||||||
|
{
|
||||||
|
if (string.IsNullOrEmpty(steamId))
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ulong.TryParse(steamId, out var value))
|
||||||
|
{
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
[Serializable]
|
[Serializable]
|
||||||
private struct LobbyPlayerInfo
|
private struct LobbyPlayerInfo
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -49,5 +49,30 @@ namespace MegaKoop.Game.Networking
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static bool TryGet(int id, out NetworkIdentity identity) => registry.TryGetValue(id, out identity);
|
public static bool TryGet(int id, out NetworkIdentity identity) => registry.TryGetValue(id, out identity);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Allows deterministic assignment so IDs match across clients.
|
||||||
|
/// </summary>
|
||||||
|
public void SetNetworkId(int id)
|
||||||
|
{
|
||||||
|
if (id == 0)
|
||||||
|
{
|
||||||
|
Debug.LogWarning("[NetworkIdentity] Cannot assign network id 0.");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (networkId == id)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (registry.TryGetValue(networkId, out NetworkIdentity existing) && existing == this)
|
||||||
|
{
|
||||||
|
registry.Remove(networkId);
|
||||||
|
}
|
||||||
|
|
||||||
|
networkId = id;
|
||||||
|
Register();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -366,7 +366,30 @@ namespace MegaKoop.UI
|
|||||||
servicesRoot.AddComponent<SteamManager>();
|
servicesRoot.AddComponent<SteamManager>();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
T EnsureComponent<T>() where T : Component
|
||||||
|
{
|
||||||
|
if (servicesRoot.TryGetComponent<T>(out var existing))
|
||||||
|
{
|
||||||
|
return existing;
|
||||||
|
}
|
||||||
|
#if UNITY_2023_1_OR_NEWER
|
||||||
|
var found = Object.FindFirstObjectByType<T>(FindObjectsInactive.Include);
|
||||||
|
#else
|
||||||
|
var found = Object.FindObjectOfType<T>();
|
||||||
|
#endif
|
||||||
|
if (found != null)
|
||||||
|
{
|
||||||
|
return found;
|
||||||
|
}
|
||||||
|
return servicesRoot.AddComponent<T>();
|
||||||
|
}
|
||||||
|
|
||||||
|
EnsureComponent<SteamLobbyManager>();
|
||||||
|
EnsureComponent<SteamP2PTransport>();
|
||||||
|
EnsureComponent<SteamCoopNetworkManager>();
|
||||||
lobbyGameCoordinator = servicesRoot.GetComponent<LobbyGameSceneCoordinator>() ?? servicesRoot.AddComponent<LobbyGameSceneCoordinator>();
|
lobbyGameCoordinator = servicesRoot.GetComponent<LobbyGameSceneCoordinator>() ?? servicesRoot.AddComponent<LobbyGameSceneCoordinator>();
|
||||||
|
|
||||||
|
DontDestroyOnLoad(servicesRoot);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user