EVERYTHING
This commit is contained in:
@@ -0,0 +1,648 @@
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Text;
|
||||
using System.Text.RegularExpressions;
|
||||
using BlockSpace.Account;
|
||||
using BlockSpace.Voxels;
|
||||
using ExitGames.Client.Photon;
|
||||
using Photon.Pun;
|
||||
using Photon.Realtime;
|
||||
using Photon.VR;
|
||||
using UnityEngine;
|
||||
using UnityEngine.Networking;
|
||||
using UnityEngine.UI;
|
||||
|
||||
namespace BlockSpace.Worlds
|
||||
{
|
||||
[DisallowMultipleComponent]
|
||||
public sealed class WorldCommandPoller : MonoBehaviourPunCallbacks
|
||||
{
|
||||
[Serializable]
|
||||
private sealed class PollRequest
|
||||
{
|
||||
public string playerId;
|
||||
}
|
||||
|
||||
[Serializable]
|
||||
private sealed class PollResponse
|
||||
{
|
||||
public bool ok;
|
||||
|
||||
public Command command;
|
||||
|
||||
public string error;
|
||||
}
|
||||
|
||||
[Serializable]
|
||||
private sealed class Command
|
||||
{
|
||||
public string type;
|
||||
|
||||
public string worldName;
|
||||
|
||||
public string roomName;
|
||||
}
|
||||
|
||||
[Serializable]
|
||||
private sealed class PresencePingRequest
|
||||
{
|
||||
public string playerId;
|
||||
|
||||
public string roomName;
|
||||
}
|
||||
|
||||
[SerializeField]
|
||||
private bool enable = true;
|
||||
|
||||
[SerializeField]
|
||||
private string backendBaseUrl = "https://blockspacebackend-production.up.railway.app";
|
||||
|
||||
[SerializeField]
|
||||
private float pollIntervalSeconds = 2f;
|
||||
|
||||
[SerializeField]
|
||||
private float onlinePingIntervalSeconds = 5f;
|
||||
|
||||
[Header("Loading Screen")]
|
||||
[SerializeField]
|
||||
private GameObject loadingScreenObject;
|
||||
|
||||
[SerializeField]
|
||||
private Slider loadingProgressSlider;
|
||||
|
||||
[SerializeField]
|
||||
private WorldLoadingScreenController loadingScreen;
|
||||
|
||||
private const string DefaultLobbyWorldName = "Lobby";
|
||||
|
||||
private const string DefaultLobbyWorldId = "ZT5HjbaGAT5adlkvAirJ0A";
|
||||
|
||||
private const int PublicWorldJoinRetryCount = 5;
|
||||
|
||||
private const string RoomWorldVersionKey = "worldVersion";
|
||||
|
||||
private Coroutine pollCoroutine;
|
||||
|
||||
private Coroutine pingCoroutine;
|
||||
|
||||
private bool joinInProgress;
|
||||
|
||||
private bool joinResultReady;
|
||||
|
||||
private bool joinSucceeded;
|
||||
|
||||
private bool leftRoomReady;
|
||||
|
||||
private bool lobbyReady;
|
||||
|
||||
private bool startupLobbyJoinRequested;
|
||||
|
||||
private new void OnEnable()
|
||||
{
|
||||
StartLoopsIfNeeded();
|
||||
}
|
||||
|
||||
private void Start()
|
||||
{
|
||||
Debug.Log("[WorldCommandPoller] Start: beginning lobby startup sequence.");
|
||||
StartCoroutine(JoinLobbyWhenBackendReady());
|
||||
}
|
||||
|
||||
private IEnumerator JoinLobbyWhenBackendReady()
|
||||
{
|
||||
BeginLoadingScreen(0.02f);
|
||||
float connectStart = Time.realtimeSinceStartup;
|
||||
while (PhotonNetwork.NetworkClientState != ClientState.ConnectedToMasterServer && Time.realtimeSinceStartup - connectStart < 15f)
|
||||
{
|
||||
yield return null;
|
||||
}
|
||||
Debug.Log($"[WorldCommandPoller] JoinLobbyWhenBackendReady: Photon state={PhotonNetwork.NetworkClientState} after wait.");
|
||||
SetLoadingProgress(0.08f);
|
||||
if (startupLobbyJoinRequested)
|
||||
{
|
||||
yield break;
|
||||
}
|
||||
string playerId = BlockSpaceAccountPrefs.GetUserFolderId();
|
||||
WorldBackendClient client = new WorldBackendClient(backendBaseUrl);
|
||||
float backendStart = Time.realtimeSinceStartup;
|
||||
while (Time.realtimeSinceStartup - backendStart < 20f)
|
||||
{
|
||||
WorldBackendClient.ResolveWorldResponse resolve = null;
|
||||
yield return client.ResolveWorld("Lobby", playerId, delegate(WorldBackendClient.ResolveWorldResponse r)
|
||||
{
|
||||
resolve = r;
|
||||
});
|
||||
if (resolve != null && resolve.ok)
|
||||
{
|
||||
Debug.Log("[WorldCommandPoller] JoinLobbyWhenBackendReady: backend resolve succeeded for Lobby.");
|
||||
SetLoadingProgress(0.14f);
|
||||
break;
|
||||
}
|
||||
if (resolve != null)
|
||||
{
|
||||
Debug.LogWarning($"[WorldCommandPoller] JoinLobbyWhenBackendReady: backend responded but resolve failed. Continuing to lobby join. ok={resolve.ok}, error={resolve.error}");
|
||||
SetLoadingProgress(0.14f);
|
||||
break;
|
||||
}
|
||||
Debug.LogWarning("[WorldCommandPoller] JoinLobbyWhenBackendReady: backend resolve returned null.");
|
||||
yield return new WaitForSecondsRealtime(1f);
|
||||
}
|
||||
startupLobbyJoinRequested = true;
|
||||
Debug.Log("[WorldCommandPoller] JoinLobbyWhenBackendReady: proceeding to join default Lobby world.");
|
||||
SetLoadingProgress(0.2f);
|
||||
yield return JoinWorldInstance("Lobby");
|
||||
yield return IncrementVisitForCurrentWorldIfMatches("Lobby");
|
||||
}
|
||||
|
||||
private IEnumerator IncrementVisitForCurrentWorldIfMatches(string baseWorldName)
|
||||
{
|
||||
if (!PhotonNetwork.InRoom || PhotonNetwork.CurrentRoom == null || !string.Equals(GetBaseWorldName(PhotonNetwork.CurrentRoom.Name), baseWorldName, StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
yield break;
|
||||
}
|
||||
string userFolderId = BlockSpaceAccountPrefs.GetUserFolderId();
|
||||
if (!string.IsNullOrEmpty(userFolderId))
|
||||
{
|
||||
WorldBackendClient client = new WorldBackendClient(backendBaseUrl);
|
||||
WorldBackendClient.ResolveWorldResponse resolve = null;
|
||||
yield return client.ResolveWorld(baseWorldName, userFolderId, delegate(WorldBackendClient.ResolveWorldResponse r)
|
||||
{
|
||||
resolve = r;
|
||||
});
|
||||
if (resolve != null && resolve.ok && resolve.exists && !string.IsNullOrEmpty(resolve.worldId))
|
||||
{
|
||||
yield return client.IncrementVisit(resolve.worldId, null);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static string RandomPrivateCode()
|
||||
{
|
||||
char c = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"[UnityEngine.Random.Range(0, "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789".Length)];
|
||||
char c2 = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"[UnityEngine.Random.Range(0, "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789".Length)];
|
||||
char c3 = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"[UnityEngine.Random.Range(0, "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789".Length)];
|
||||
return new string(new char[3] { c, c2, c3 });
|
||||
}
|
||||
|
||||
private IEnumerator JoinPrivateWorldInstance(string worldName)
|
||||
{
|
||||
for (int attempt = 0; attempt < 10; attempt++)
|
||||
{
|
||||
string text = RandomPrivateCode();
|
||||
string roomName = worldName + "|" + text;
|
||||
yield return JoinExactRoom(roomName);
|
||||
if (PhotonNetwork.InRoom && PhotonNetwork.CurrentRoom != null && string.Equals(PhotonNetwork.CurrentRoom.Name, roomName, StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private new void OnDisable()
|
||||
{
|
||||
StopAllCoroutines();
|
||||
pollCoroutine = null;
|
||||
pingCoroutine = null;
|
||||
SetLoadingScreen(visible: false, 0f);
|
||||
}
|
||||
|
||||
private void StartLoopsIfNeeded()
|
||||
{
|
||||
if (enable)
|
||||
{
|
||||
if (pollCoroutine == null)
|
||||
{
|
||||
pollCoroutine = StartCoroutine(PollLoop());
|
||||
}
|
||||
if (pingCoroutine == null)
|
||||
{
|
||||
pingCoroutine = StartCoroutine(PresencePingLoop());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void SetLoadingScreen(bool visible, float progress)
|
||||
{
|
||||
WorldLoadingScreenController worldLoadingScreenController = ResolveLoadingScreen();
|
||||
if (!(worldLoadingScreenController == null))
|
||||
{
|
||||
worldLoadingScreenController.SetLoading(visible);
|
||||
worldLoadingScreenController.SetProgress(progress);
|
||||
}
|
||||
}
|
||||
|
||||
private void BeginLoadingScreen(float progress)
|
||||
{
|
||||
WorldLoadingScreenController worldLoadingScreenController = ResolveLoadingScreen();
|
||||
if (!(worldLoadingScreenController == null))
|
||||
{
|
||||
worldLoadingScreenController.BeginLoading(progress);
|
||||
}
|
||||
}
|
||||
|
||||
private void SetLoadingProgress(float progress)
|
||||
{
|
||||
WorldLoadingScreenController worldLoadingScreenController = ResolveLoadingScreen();
|
||||
if (!(worldLoadingScreenController == null))
|
||||
{
|
||||
worldLoadingScreenController.SetCheckpoint(progress);
|
||||
}
|
||||
}
|
||||
|
||||
private WorldLoadingScreenController ResolveLoadingScreen()
|
||||
{
|
||||
if (loadingScreen == null)
|
||||
{
|
||||
loadingScreen = ((WorldLoadingScreenController.Instance != null) ? WorldLoadingScreenController.Instance : UnityEngine.Object.FindFirstObjectByType<WorldLoadingScreenController>());
|
||||
}
|
||||
if (loadingScreen == null && loadingScreenObject != null)
|
||||
{
|
||||
loadingScreen = base.gameObject.AddComponent<WorldLoadingScreenController>();
|
||||
}
|
||||
if (loadingScreen != null)
|
||||
{
|
||||
loadingScreen.Configure(loadingScreenObject, loadingProgressSlider);
|
||||
}
|
||||
return loadingScreen;
|
||||
}
|
||||
|
||||
private IEnumerator PresencePingLoop()
|
||||
{
|
||||
while (enable)
|
||||
{
|
||||
yield return new WaitForSecondsRealtime(Mathf.Clamp(onlinePingIntervalSeconds, 1f, 60f));
|
||||
if (!BlockSpaceAccountPrefs.IsLinked)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
string linkedPlayerId = BlockSpaceAccountPrefs.GetLinkedPlayerId();
|
||||
if (!string.IsNullOrEmpty(linkedPlayerId))
|
||||
{
|
||||
string url = (backendBaseUrl ?? string.Empty).Trim().TrimEnd('/') + "/api/presence/ping";
|
||||
string roomName = ((PhotonNetwork.InRoom && PhotonNetwork.CurrentRoom != null) ? PhotonNetwork.CurrentRoom.Name : "");
|
||||
string s = JsonUtility.ToJson(new PresencePingRequest
|
||||
{
|
||||
playerId = linkedPlayerId,
|
||||
roomName = roomName
|
||||
});
|
||||
using UnityWebRequest request = new UnityWebRequest(url, "POST");
|
||||
byte[] bytes = Encoding.UTF8.GetBytes(s);
|
||||
request.uploadHandler = new UploadHandlerRaw(bytes);
|
||||
request.downloadHandler = new DownloadHandlerBuffer();
|
||||
request.SetRequestHeader("Content-Type", "application/json");
|
||||
yield return request.SendWebRequest();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private IEnumerator PollLoop()
|
||||
{
|
||||
while (enable)
|
||||
{
|
||||
yield return new WaitForSecondsRealtime(Mathf.Clamp(pollIntervalSeconds, 0.5f, 30f));
|
||||
if (!BlockSpaceAccountPrefs.IsLinked || joinInProgress)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
string linkedPlayerId = BlockSpaceAccountPrefs.GetLinkedPlayerId();
|
||||
if (string.IsNullOrEmpty(linkedPlayerId))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
string text = (backendBaseUrl ?? string.Empty).Trim().TrimEnd('/');
|
||||
if (string.IsNullOrEmpty(text))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
string url = text + "/api/commands/poll";
|
||||
string s = JsonUtility.ToJson(new PollRequest
|
||||
{
|
||||
playerId = linkedPlayerId
|
||||
});
|
||||
PollResponse response = null;
|
||||
using (UnityWebRequest request = new UnityWebRequest(url, "POST"))
|
||||
{
|
||||
byte[] bytes = Encoding.UTF8.GetBytes(s);
|
||||
request.uploadHandler = new UploadHandlerRaw(bytes);
|
||||
request.downloadHandler = new DownloadHandlerBuffer();
|
||||
request.SetRequestHeader("Content-Type", "application/json");
|
||||
yield return request.SendWebRequest();
|
||||
if (request.result == UnityWebRequest.Result.Success)
|
||||
{
|
||||
try
|
||||
{
|
||||
response = JsonUtility.FromJson<PollResponse>(request.downloadHandler.text);
|
||||
}
|
||||
catch
|
||||
{
|
||||
}
|
||||
}
|
||||
}
|
||||
if (response == null || !response.ok || response.command == null)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
if (!string.Equals(response.command.type, "join_world", StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
if (string.Equals(response.command.type, "world_reload", StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
string text2 = (response.command.worldName ?? string.Empty).Trim();
|
||||
if (!string.IsNullOrEmpty(text2))
|
||||
{
|
||||
yield return JoinWorldInstance(text2);
|
||||
}
|
||||
}
|
||||
else if (string.Equals(response.command.type, "world_force_save", StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
string text3 = (response.command.worldName ?? string.Empty).Trim();
|
||||
if (!string.IsNullOrEmpty(text3))
|
||||
{
|
||||
yield return ForceSaveWorld(text3);
|
||||
}
|
||||
}
|
||||
else if (string.Equals(response.command.type, "join_room", StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
string text4 = (response.command.roomName ?? string.Empty).Trim();
|
||||
if (!string.IsNullOrEmpty(text4))
|
||||
{
|
||||
yield return JoinExactRoom(text4);
|
||||
}
|
||||
}
|
||||
else if (string.Equals(response.command.type, "join_world_private", StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
string text5 = (response.command.worldName ?? string.Empty).Trim();
|
||||
if (!string.IsNullOrEmpty(text5))
|
||||
{
|
||||
yield return JoinPrivateWorldInstance(text5);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
string text6 = (response.command.worldName ?? string.Empty).Trim();
|
||||
if (!string.IsNullOrEmpty(text6))
|
||||
{
|
||||
yield return JoinWorldInstance(text6);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static string GetBaseWorldName(string roomName)
|
||||
{
|
||||
string text = (roomName ?? string.Empty).Trim();
|
||||
if (string.IsNullOrEmpty(text))
|
||||
{
|
||||
return text;
|
||||
}
|
||||
int num = text.LastIndexOf('|');
|
||||
if (num <= 0)
|
||||
{
|
||||
return text;
|
||||
}
|
||||
string text2 = text.Substring(num + 1);
|
||||
if (text2.Length == 3 && Regex.IsMatch(text2, "^[A-Za-z0-9]{3}$"))
|
||||
{
|
||||
return text.Substring(0, num);
|
||||
}
|
||||
return text;
|
||||
}
|
||||
|
||||
private IEnumerator ForceSaveWorld(string baseWorldName)
|
||||
{
|
||||
if (PhotonNetwork.InRoom && PhotonNetwork.CurrentRoom != null && string.Equals(GetBaseWorldName(PhotonNetwork.CurrentRoom.Name), baseWorldName, StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
VoxelGroupPhotonSync voxelGroupPhotonSync = UnityEngine.Object.FindFirstObjectByType<VoxelGroupPhotonSync>();
|
||||
if (!(voxelGroupPhotonSync == null))
|
||||
{
|
||||
yield return voxelGroupPhotonSync.ForceSaveNow();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private IEnumerator JoinWorldInstance(string worldName)
|
||||
{
|
||||
Debug.Log("[WorldCommandPoller] JoinWorldInstance: starting join for world '" + worldName + "'.");
|
||||
joinInProgress = true;
|
||||
BeginLoadingScreen(0.2f);
|
||||
if (PhotonNetwork.InRoom)
|
||||
{
|
||||
SetLoadingProgress(0.24f);
|
||||
Debug.Log("[WorldCommandPoller] JoinWorldInstance: leaving current room '" + PhotonNetwork.CurrentRoom?.Name + "'.");
|
||||
leftRoomReady = false;
|
||||
PhotonNetwork.LeaveRoom();
|
||||
float start = Time.realtimeSinceStartup;
|
||||
while (!leftRoomReady && Time.realtimeSinceStartup - start < 10f)
|
||||
{
|
||||
yield return null;
|
||||
}
|
||||
SetLoadingProgress(0.3f);
|
||||
Debug.Log($"[WorldCommandPoller] JoinWorldInstance: left room ready={leftRoomReady}, inRoom={PhotonNetwork.InRoom}.");
|
||||
}
|
||||
SetLoadingProgress(0.34f);
|
||||
float masterStart = Time.realtimeSinceStartup;
|
||||
while (PhotonNetwork.NetworkClientState != ClientState.ConnectedToMasterServer && Time.realtimeSinceStartup - masterStart < 10f)
|
||||
{
|
||||
yield return null;
|
||||
}
|
||||
SetLoadingProgress(0.4f);
|
||||
if (PhotonNetwork.NetworkClientState != ClientState.ConnectedToMasterServer)
|
||||
{
|
||||
joinInProgress = false;
|
||||
SetLoadingScreen(visible: false, 0f);
|
||||
yield break;
|
||||
}
|
||||
WorldBackendClient client = new WorldBackendClient(backendBaseUrl);
|
||||
int maxPlayers = ((PhotonVRManager.Manager != null) ? PhotonVRManager.Manager.DefaultRoomLimit : 16);
|
||||
for (int attempt = 0; attempt < 5; attempt++)
|
||||
{
|
||||
SetLoadingProgress(0.46f);
|
||||
WorldBackendClient.LobbyTargetResponse target = null;
|
||||
yield return client.ResolveLobbyTarget(worldName, maxPlayers, delegate(WorldBackendClient.LobbyTargetResponse r)
|
||||
{
|
||||
target = r;
|
||||
});
|
||||
if (target == null || !target.ok || string.IsNullOrEmpty(target.roomName))
|
||||
{
|
||||
Debug.LogWarning(string.Format("[WorldCommandPoller] JoinWorldInstance: lobby target failed for '{0}' [attempt {1}/{2}]. error={3}", worldName, attempt + 1, 5, (target != null) ? target.error : "<null>"));
|
||||
yield return new WaitForSecondsRealtime(1f);
|
||||
continue;
|
||||
}
|
||||
joinResultReady = false;
|
||||
joinSucceeded = false;
|
||||
SetLoadingProgress(0.54f);
|
||||
ExitGames.Client.Photon.Hashtable hashtable = new ExitGames.Client.Photon.Hashtable();
|
||||
if (!string.IsNullOrEmpty(target.worldVersion))
|
||||
{
|
||||
hashtable["worldVersion"] = target.worldVersion;
|
||||
}
|
||||
RoomOptions roomOptions = new RoomOptions();
|
||||
roomOptions.IsVisible = true;
|
||||
roomOptions.IsOpen = true;
|
||||
roomOptions.MaxPlayers = (byte)Mathf.Clamp(maxPlayers, 1, 255);
|
||||
roomOptions.CustomRoomProperties = hashtable;
|
||||
roomOptions.CustomRoomPropertiesForLobby = new string[1] { "worldVersion" };
|
||||
RoomOptions roomOptions2 = roomOptions;
|
||||
Debug.Log($"[WorldCommandPoller] JoinWorldInstance: backend selected {target.action}('{target.roomName}') worldVersion='{target.worldVersion}' roomsSeen={target.roomsSeen} [attempt {attempt + 1}/{5}].");
|
||||
if (string.Equals(target.action, "join", StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
SetLoadingProgress(0.6f);
|
||||
PhotonNetwork.JoinRoom(target.roomName);
|
||||
}
|
||||
else
|
||||
{
|
||||
SetLoadingProgress(0.6f);
|
||||
PhotonNetwork.JoinOrCreateRoom(target.roomName, roomOptions2, null);
|
||||
}
|
||||
float start = Time.realtimeSinceStartup;
|
||||
while (!joinResultReady && Time.realtimeSinceStartup - start < 12f)
|
||||
{
|
||||
yield return null;
|
||||
}
|
||||
if (!joinResultReady && PhotonNetwork.InRoom && PhotonNetwork.CurrentRoom != null && string.Equals(PhotonNetwork.CurrentRoom.Name, target.roomName, StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
joinSucceeded = true;
|
||||
joinResultReady = true;
|
||||
Debug.Log("[WorldCommandPoller] JoinWorldInstance: detected successful join by current room '" + target.roomName + "' without callback.");
|
||||
}
|
||||
Debug.Log($"[WorldCommandPoller] JoinWorldInstance: room '{target.roomName}' join result ready={joinResultReady}, succeeded={joinSucceeded}, inRoom={PhotonNetwork.InRoom}, currentRoom={PhotonNetwork.CurrentRoom?.Name}.");
|
||||
if (joinSucceeded && PhotonNetwork.InRoom)
|
||||
{
|
||||
Debug.Log("[WorldCommandPoller] JoinWorldInstance: successfully joined room '" + target.roomName + "'.");
|
||||
joinInProgress = false;
|
||||
SetLoadingProgress(0.66f);
|
||||
yield break;
|
||||
}
|
||||
if (PhotonNetwork.InRoom && PhotonNetwork.CurrentRoom != null && !string.Equals(PhotonNetwork.CurrentRoom.Name, target.roomName, StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
Debug.LogWarning("[WorldCommandPoller] JoinWorldInstance: still in different room '" + PhotonNetwork.CurrentRoom.Name + "' after attempting '" + target.roomName + "', leaving before next attempt.");
|
||||
leftRoomReady = false;
|
||||
PhotonNetwork.LeaveRoom();
|
||||
float leaveStart = Time.realtimeSinceStartup;
|
||||
while (!leftRoomReady && Time.realtimeSinceStartup - leaveStart < 10f)
|
||||
{
|
||||
yield return null;
|
||||
}
|
||||
SetLoadingProgress(0.3f);
|
||||
}
|
||||
yield return new WaitForSecondsRealtime(0.5f);
|
||||
}
|
||||
joinInProgress = false;
|
||||
SetLoadingScreen(visible: false, 0f);
|
||||
}
|
||||
|
||||
private IEnumerator JoinExactRoom(string roomName)
|
||||
{
|
||||
Debug.Log("[WorldCommandPoller] JoinExactRoom: starting join for exact room '" + roomName + "'.");
|
||||
joinInProgress = true;
|
||||
BeginLoadingScreen(0.2f);
|
||||
if (PhotonNetwork.InRoom)
|
||||
{
|
||||
SetLoadingProgress(0.24f);
|
||||
Debug.Log("[WorldCommandPoller] JoinExactRoom: leaving current room '" + PhotonNetwork.CurrentRoom?.Name + "'.");
|
||||
leftRoomReady = false;
|
||||
PhotonNetwork.LeaveRoom();
|
||||
float start = Time.realtimeSinceStartup;
|
||||
while (!leftRoomReady && Time.realtimeSinceStartup - start < 10f)
|
||||
{
|
||||
yield return null;
|
||||
}
|
||||
SetLoadingProgress(0.3f);
|
||||
Debug.Log($"[WorldCommandPoller] JoinExactRoom: left room ready={leftRoomReady}, inRoom={PhotonNetwork.InRoom}.");
|
||||
}
|
||||
SetLoadingProgress(0.34f);
|
||||
float masterStart = Time.realtimeSinceStartup;
|
||||
while (PhotonNetwork.NetworkClientState != ClientState.ConnectedToMasterServer && Time.realtimeSinceStartup - masterStart < 10f)
|
||||
{
|
||||
yield return null;
|
||||
}
|
||||
SetLoadingProgress(0.4f);
|
||||
if (PhotonNetwork.NetworkClientState != ClientState.ConnectedToMasterServer)
|
||||
{
|
||||
joinInProgress = false;
|
||||
SetLoadingScreen(visible: false, 0f);
|
||||
yield break;
|
||||
}
|
||||
if (!PhotonNetwork.InLobby)
|
||||
{
|
||||
lobbyReady = false;
|
||||
PhotonNetwork.JoinLobby();
|
||||
float start = Time.realtimeSinceStartup;
|
||||
while (!lobbyReady && Time.realtimeSinceStartup - start < 10f)
|
||||
{
|
||||
yield return null;
|
||||
}
|
||||
SetLoadingProgress(0.5f);
|
||||
if (!PhotonNetwork.InLobby)
|
||||
{
|
||||
joinInProgress = false;
|
||||
SetLoadingScreen(visible: false, 0f);
|
||||
yield break;
|
||||
}
|
||||
}
|
||||
joinResultReady = false;
|
||||
joinSucceeded = false;
|
||||
RoomOptions roomOptions = new RoomOptions
|
||||
{
|
||||
IsVisible = true,
|
||||
IsOpen = true,
|
||||
MaxPlayers = ((PhotonVRManager.Manager != null) ? ((byte)PhotonVRManager.Manager.DefaultRoomLimit) : 16)
|
||||
};
|
||||
Debug.Log("[WorldCommandPoller] JoinExactRoom: requesting JoinOrCreateRoom('" + roomName + "').");
|
||||
SetLoadingProgress(0.6f);
|
||||
PhotonNetwork.JoinOrCreateRoom(roomName, roomOptions, null);
|
||||
float waitStart = Time.realtimeSinceStartup;
|
||||
while (!joinResultReady && Time.realtimeSinceStartup - waitStart < 10f)
|
||||
{
|
||||
yield return null;
|
||||
}
|
||||
Debug.Log($"[WorldCommandPoller] JoinExactRoom: room '{roomName}' join result ready={joinResultReady}, succeeded={joinSucceeded}, inRoom={PhotonNetwork.InRoom}.");
|
||||
joinInProgress = false;
|
||||
if (joinSucceeded && PhotonNetwork.InRoom)
|
||||
{
|
||||
SetLoadingProgress(0.66f);
|
||||
}
|
||||
else
|
||||
{
|
||||
SetLoadingScreen(visible: false, 0f);
|
||||
}
|
||||
}
|
||||
|
||||
public override void OnLeftRoom()
|
||||
{
|
||||
leftRoomReady = true;
|
||||
base.OnLeftRoom();
|
||||
}
|
||||
|
||||
public override void OnJoinedRoom()
|
||||
{
|
||||
joinSucceeded = true;
|
||||
joinResultReady = true;
|
||||
Debug.Log("[WorldCommandPoller] OnJoinedRoom: joined room '" + PhotonNetwork.CurrentRoom?.Name + "' successfully.");
|
||||
base.OnJoinedRoom();
|
||||
}
|
||||
|
||||
public override void OnJoinedLobby()
|
||||
{
|
||||
lobbyReady = true;
|
||||
Debug.Log("[WorldCommandPoller] OnJoinedLobby: Photon lobby joined successfully.");
|
||||
base.OnJoinedLobby();
|
||||
}
|
||||
|
||||
public override void OnJoinRoomFailed(short returnCode, string message)
|
||||
{
|
||||
joinSucceeded = false;
|
||||
joinResultReady = true;
|
||||
Debug.LogWarning($"[WorldCommandPoller] OnJoinRoomFailed: code={returnCode}, message={message}, state={PhotonNetwork.NetworkClientState}.");
|
||||
base.OnJoinRoomFailed(returnCode, message);
|
||||
}
|
||||
|
||||
public override void OnCreateRoomFailed(short returnCode, string message)
|
||||
{
|
||||
joinSucceeded = false;
|
||||
joinResultReady = true;
|
||||
Debug.LogWarning($"[WorldCommandPoller] OnCreateRoomFailed: code={returnCode}, message={message}, state={PhotonNetwork.NetworkClientState}.");
|
||||
base.OnCreateRoomFailed(returnCode, message);
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user