Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
using UnityEngine;
using UnityEngine.Assertions;
using UnityEngine.UI;
using UnityEngine.SceneManagement;
using UnityEngine.Networking;
using UnityEngine.Networking.Types;
using UnityEngine.Networking.Match;
using System.Collections;
namespace Prototype.NetworkLobby
{
// private class ExtMsgType : MsgType {
// public const short PlayerID = 64;
// }
public class LobbyManager : NetworkLobbyManager
{
static public LobbyManager s_Singleton;
[Header("Unity UI Lobby")]
[Tooltip("Time in second between all players ready & match start")]
public float prematchCountdown = 5.0f;
[Space]
[Header("UI Reference")]
public LobbyTopPanel topPanel;
public RectTransform mainMenuPanel;
public RectTransform lanPanel;
public RectTransform mmServerPanel;
public LobbyInfoPanel infoPanel;
public LobbyCountdownPanel countdownPanel;
public GameObject addPlayerButton;
public Button backButton;
public Text statusInfo;
public Text hostInfo;
public InputField matchNameInput;
public InputField ipInput;
public AutoMatch autoMatch;
//Client numPlayers from NetworkManager is always 0, so we count (throught connect/destroy in LobbyPlayer) the number
//of players, so that even client know how many player there is.
[HideInInspector]
public int _playerNumber = 0;
//used to disconnect a client properly when exiting the matchmaker
[HideInInspector]
public bool _isMatchmaking = false;
public delegate void BackButtonDelegate();
public BackButtonDelegate backDelegate;
protected bool _disconnectServer = false;
protected ulong _currentMatchID;
protected LobbyHook _lobbyHook;
protected RectTransform currentPanel;
class KickMsg : MessageBase { }
static short _msgKicked = MsgType.Highest + Constants.MSG_KICKED;
string _debugString;
string _debugString2;
bool _debugAll = false;
// MonoBehaviour callbacks
// WARNING: don't use 'Awake' in the LobbyManager script! https://goo.gl/Bo2yhe
// void Awake() { }
void Start()
{
s_Singleton = this;
_lobbyHook = GetComponent<LobbyHook>();
currentPanel = mainMenuPanel;
//backButton.gameObject.SetActive(false);
backDelegate = () => GoHome();
DontDestroyOnLoad(gameObject);
SetServerInfo("Offline", "None");
SceneManager.sceneLoaded += OnLevelFinishedLoading;
}
void OnDestroy()
{
SceneManager.sceneLoaded -= OnLevelFinishedLoading;
}
// End-of-MB callbacks
// --------
// LobbyNetworkManager overrides I: server handlers (OnServerConnect, OnServerDisconnect,
// OnServerAddPlayer, OnServerRemovePlayer, ServerChangeScene, OnServerSceneChanged)
public override void OnServerConnect(NetworkConnection conn)
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnServerConnect: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
base.OnServerConnect (conn);
}
public override void OnServerDisconnect(NetworkConnection conn)
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnServerDisconnect: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
//if (_debugAll) {
// ClientDebugUI.i.Log (_debugString, GameColor.Red);
// Debug.Log (_debugString);
//}
base.OnServerDisconnect (conn);
GoHome (); // for now, for safty/stability sake, test on devices using this method (on server disconnect)
}
public override void OnServerAddPlayer(NetworkConnection conn, short playerControllerId)
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnServerAddPlayer: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
base.OnServerAddPlayer(conn, playerControllerId);
}
public override void OnServerRemovePlayer(NetworkConnection conn, PlayerController player)
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnServerRemovePlayer: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
base.OnServerRemovePlayer(conn, player);
}
public override void ServerChangeScene(string sceneName)
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.ServerChangeScene: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
// SUPER-HACK! (NetworkLobbyManager source: https://goo.gl/2cgIPE)
for (int i = 0; i < lobbySlots.Length; i++) {
var lobbyPlayer = lobbySlots [i];
if (lobbyPlayer == null)
continue;
var uv = lobbyPlayer.GetComponent<NetworkIdentity> ();
//PlayerController playerController;
//if (uv.connectionToClient.playerControllers.Count == 0)
if (uv.connectionToClient == null)
{
return;
}
}
base.ServerChangeScene (sceneName);
}
public override void OnServerSceneChanged(string sceneName)
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnServerSceneChanged: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
base.OnServerSceneChanged (sceneName);
}
// End-of-LobbyNetworkManager overrides I:
// --------
// LobbyNetworkManager overrides II: (OnStartServer, OnStartHost, OnStopHost, OnStartClient,
// OnClientConnect, OnClientDisconnect, OnStopClient, OnClientSceneChanged)
public override void OnStartServer ()
{
_debugString = string.Format ("LobbyManager.OnStartServer: {0}", "");
Debug.Log (_debugString);
ServerDebugUI.i.Log (_debugString, GameColor.Blue);
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnStartServer: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
base.OnStartServer ();
}
public override void OnStartHost()
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnStartHost: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
base.OnStartHost(); // NetworkLobbyManager.OnStartHost calls empty stub NetworkLobbyManager.OnLobbyStartHost (overwritten below)
ChangeTo(lanPanel);
backDelegate = StopHostClbk;
SetServerInfo("Hosting", networkAddress);
}
public override void OnStopHost()
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnStopHost: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
base.OnStopHost(); // NetworkLobbyManager.OnStopHost calls empty stub NetworkLobbyManager.OnLobbyStopHost (overwritten below)
}
public override void OnStartClient(NetworkClient lobbyClient)
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnStartClient: +{0} ({1})", bonus, autoMatch.timeout.ToString ("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
base.OnStartClient (lobbyClient);
}
public override void OnClientConnect(NetworkConnection conn)
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnClientConnect: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
infoPanel.gameObject.SetActive(false);
conn.RegisterHandler(_msgKicked, KickedMessageHandler);
// register custom message with client (necessary?)
conn.RegisterHandler(CustomMessage.SetParent, OnSetParent);
base.OnClientConnect(conn);
if (!NetworkServer.active)
{ //only to do on pure client (not self hosting client)
ChangeTo(lanPanel);
backDelegate = StopClientClbk;
SetServerInfo("Client", networkAddress);
}
}
public override void OnClientDisconnect(NetworkConnection conn)
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
if (_debugAll) {
_debugString = string.Format ("LobbyManager.OnClientDisconnect: +{0} ({1})", bonus, autoMatch.timeout.ToString ("0.00"));
ClientDebugUI.i.Log (_debugString, GameColor.Red);
Debug.Log (_debugString);
}
base.OnClientDisconnect(conn);
GoHome (); // for now, for safty/stability sake, test on devices using this method (on client disconnect)
// close info panel (AMM addition, 16 Nov 2016)
// infoPanel.gameObject.SetActive(false);
// ChangeTo(mainMenuPanel);
}
public override void OnStopClient()
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnStopClient: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Yellow);
Debug.Log (_debugString);
}
base.OnStopClient ();
}
public override void OnClientSceneChanged (NetworkConnection conn)
{
float bonus = 0.0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnClientSceneChanged: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
base.OnClientSceneChanged (conn);
}
// End-of-LobbyNetworkManager overrides II:
// --------
// LobbyNetworkManager overrides III: OnLobbyStartHost, OnLobbyStopHost, OnLobbyStartServer, OnLobbyServerConnect, OnLobbyServerDisconnect,
// OnLobbyServerSceneChanged, OnLobbyServerCreateLobbyPlayer, OnLobbyServerCreateGamePlayer, OnLobbyServerPlayerRemoved, OnLobbyServerSceneLoadedForPlayer,
// OnLobbyServerPlayersReady, OnLobbyClientEnter, OnLobbyClientExit, OnLobbyClientConnect, OnLobbyClientDisconnect, OnLobbyStartClient, OnLobbyStopClient,
// OnLobbyClientSceneChanged, OnLobbyClientAddPlayerFailed
public override void OnLobbyStartHost()
{
float bonus = 0.0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnLobbyStartHost: +{0} ({1})", bonus, autoMatch.timeout.ToString ("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
base.OnLobbyStartHost ();
}
public override void OnLobbyStopHost()
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnLobbyStopHost: +{0} ({1})", bonus, autoMatch.timeout.ToString ("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
base.OnLobbyStopHost ();
}
public override void OnLobbyStartServer()
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnLobbyStartServer: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
base.OnLobbyStartServer ();
}
public override void OnLobbyServerConnect(NetworkConnection conn)
{
float bonus = 0.0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnLobbyServerConnect: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
base.OnLobbyServerConnect (conn);
}
public override void OnLobbyServerDisconnect(NetworkConnection conn)
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnLobbyServerDisconnect: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
//if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Yellow);
Debug.Log (_debugString);
//}
for (int i = 0; i < lobbySlots.Length; ++i)
{
LobbyPlayer p = lobbySlots[i] as LobbyPlayer;
if (p != null)
{
p.RpcUpdateRemoveButton();
p.ToggleJoinButton(numPlayers >= minPlayers);
}
}
}
public override void OnLobbyServerSceneChanged(string sceneName)
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnLobbyServerSceneChanged: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Yellow);
Debug.Log (_debugString);
}
base.OnLobbyServerSceneChanged (sceneName);
}
// we want to disable the button JOIN if we don't have enough players, but
// OnLobbyClientConnect isn't called on hosting player. So we override the lobbyPlayer creation
public override GameObject OnLobbyServerCreateLobbyPlayer(NetworkConnection conn, short playerControllerId)
{
// NOTE: virtual function NetworkLobbyManager.OnLobbyServerCreateLobbyPlayer returns 'null'
// base.OnLobbyServerCreateLobbyPlayer (conn, playerControllerId);
Assert.IsNotNull(lobbyPlayerPrefab);
Assert.IsNotNull(lobbyPlayerPrefab.gameObject);
// sanity-check
if (!NetworkServer.active) {
string debugString = string.Format ("LobbyManager.OnLobbyServerCreateLobbyPlayer: NetworkServer not active (unexpected), returning null", "");
ClientDebugUI.i.Log (debugString, GameColor.Red);
Debug.LogError(debugString);
return null;
}
string idString = "null".Colorize(GameColor.Red);
if (conn != null)
{
idString = "conn.id=" + conn.connectionId;
}
// add some auto-matching bonus time if we are the host and a remote client connected
var bonus = 0f;
if (conn.connectionId > 0) {
bonus += 6f;
}
autoMatch.AddTimeout(bonus);
_debugString = string.Format ("LobbyManager.OnLobbyServerCreateLobbyPlayer ({0}): +{1} ({2})\n{3}",
idString, bonus, autoMatch.timeout.ToString("0.00"), conn.PrettyPrint(false, " ", true));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
GameObject obj = Instantiate(lobbyPlayerPrefab.gameObject) as GameObject;
LobbyPlayer newPlayer = obj.GetComponent<LobbyPlayer>();
newPlayer.ToggleJoinButton(numPlayers + 1 >= minPlayers);
for (int i = 0; i < lobbySlots.Length; ++i)
{
LobbyPlayer p = lobbySlots[i] as LobbyPlayer;
if (p != null)
{
p.RpcUpdateRemoveButton();
p.ToggleJoinButton(numPlayers + 1 >= minPlayers);
}
}
return obj;
}
public override GameObject OnLobbyServerCreateGamePlayer(NetworkConnection conn, short playerControllerId)
{
float bonus = 0.0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnLobbyServerCreateGamePlayer: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
// NOTE: virtual function NetworkLobbyManager.OnLobbyServerCreateGamePlayer below just returns 'null'
//base.OnLobbyServerCreateGamePlayer (conn, playerControllerId);
return null;
}
public override void OnLobbyServerPlayerRemoved(NetworkConnection conn, short playerControllerId)
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnLobbyServerPlayerRemoved: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
for (int i = 0; i < lobbySlots.Length; ++i)
{
LobbyPlayer p = lobbySlots[i] as LobbyPlayer;
if (p != null)
{
p.RpcUpdateRemoveButton();
p.ToggleJoinButton(numPlayers + 1 >= minPlayers);
}
}
}
// NOTE: called towards the end of the NetworkLobbyManager.SceneLoadedForPlayer function. From the Unity
// docs: "This is called on the server when it is told that a client has finished switching from the
// lobby scene to a game player scene." NOTE: if we return 'false', the lobby player will not be replaced
// with the game player (i.e. NetworkLobbyManager.SceneLoadedForPlayer will return early before
// NetworkServer.ReplacePlayerForConnection is called)
public override bool OnLobbyServerSceneLoadedForPlayer(GameObject lobbyPlayerGO, GameObject gamePlayer)
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnLobbyServerSceneLoadedForPlayer: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
LobbyPlayer lobbyPlayer = lobbyPlayerGO.GetComponent<LobbyPlayer> ();
if (lobbyPlayer == null)
{
ClientDebugUI.i.Log (string.Format ("LobbyManager.OnLobbyServerSceneLoadedForPlayer:\n LobbyPlayer" +
" component not found on lobbyPlayer, returning false"), GameColor.Red);
return false;
}
// this script runs on the NetworkPlayer prefab (i.e. the online scene player
// prefab assigned to the lobby manager's 'Game Player Prefab' slot)
Player networkPlayer = gamePlayer.GetComponent<Player> ();
if (networkPlayer == null)
{
ClientDebugUI.i.Log (string.Format ("LobbyManager.OnLobbyServerSceneLoadedForPlayer:\n NetworkPlayer" +
" component not found on gamePlayer {0}, returning false", gamePlayer.name), GameColor.Red);
return false;
}
// this hook allows you to apply state data from the lobby-player to the game-player
// just subclass "LobbyHook" and add it to the lobby object.
if (_lobbyHook)
{
//ServerDebugUI.i.Log (string.Format ("LobbyManager.OnLobbyServerSceneLoadedForPlayer: hook for player {0} found", lobbyPlayerGO.name));
// execute the lobby hook logic (presumably utilizing info from the lobby player to setup teh game player)
_lobbyHook.OnLobbyServerSceneLoadedForPlayer (this, lobbyPlayerGO, gamePlayer);
}
return true;
}
public override void OnLobbyServerPlayersReady()
{
float bonus = 0.0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnLobbyServerPlayersReady: +{0} ({1}) lobbySlots.Length={2}", bonus, autoMatch.timeout.ToString("0.00"), lobbySlots.Length);
if (_debugAll) {
ClientDebugUI.i.Log (_debugString);
Debug.Log (_debugString);
}
bool allready = true;
for(int i = 0; i < lobbySlots.Length; ++i)
{
if (lobbySlots [i] != null) {
allready &= lobbySlots [i].readyToBegin;
}
}
if (allready) {
StartCoroutine (ServerCountdownCoroutine ());
}
}
public override void OnLobbyClientEnter ()
{
//base.OnLobbyClientEnter (); // empty virtual stub
float bonus = 0.0f;
autoMatch.AddTimeout (bonus);
if (_debugAll) {
_debugString = string.Format ("LobbyManager.OnLobbyClientEnter: +{0} ({1})", bonus, autoMatch.timeout.ToString ("0.00"));
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
}
}
public override void OnLobbyClientExit()
{
//base.OnLobbyClientExit (); // empty virtual stub
float bonus = 0f;
autoMatch.AddTimeout (bonus);
if (_debugAll) {
_debugString = string.Format ("LobbyManager.OnLobbyClientExit: +{0} ({1})", bonus, autoMatch.timeout.ToString ("0.00"));
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
}
}
// NOTE: only seems to be called for 'pure' clients
public override void OnLobbyClientConnect(NetworkConnection conn)
{
//base.OnLobbyClientConnect (conn); // empty virtual stub
string idString = "null".Colorize (GameColor.Red);
if (conn != null) {
idString = "conn.id=" + conn.connectionId;
}
var bonus = 0f;
// add some auto-matching bonus time when we connect as a (remote) client
if (!NetworkServer.active && conn.connectionId > 0) {
bonus += 6f;
}
autoMatch.AddTimeout (bonus);
if (_debugAll) {
_debugString = string.Format ("LobbyManager.OnLobbyClientConnect ({0}): +{1} ({2})", idString, bonus, autoMatch.timeout.ToString ("0.00"));
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
}
}
public override void OnLobbyClientDisconnect(NetworkConnection conn)
{
//base.OnLobbyClientDisconnect (conn); // empty virtual stub
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnLobbyClientDisconnect: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
ClientDebugUI.i.Log (_debugString, GameColor.Red);
}
public override void OnLobbyStartClient(NetworkClient lobbyClient)
{
//base.OnLobbyStartClient (lobbyClient); // empty virtual stub
float bonus = 0.0f;
string idString = "null".Colorize(GameColor.Red);
if (lobbyClient.connection != null)
{
idString = "conn.id=" + lobbyClient.connection.connectionId;
}
if (!autoMatch.useLANToggle) {
bonus = 2f; // need longer when matchmaking
}
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnLobbyStartClient ({0}): +{1} ({2})", idString, bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
}
public override void OnLobbyStopClient()
{
//base.OnLobbyStopClient (); // empty virtual stub
float bonus = 0.0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnLobbyStopClient: +{0} ({1})", bonus, autoMatch.timeout.ToString ("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString);
Debug.Log (_debugString);
}
}
public override void OnLobbyClientSceneChanged(NetworkConnection conn)
{
//base.OnLobbyClientSceneChanged (); // empty virtual stub
float bonus = 0.0f;
autoMatch.AddTimeout (bonus);
if (_debugAll) {
_debugString = string.Format ("LobbyManager.OnLobbyClientSceneChanged: +{0} (scene at 0={1}, sceneCount={2})", bonus, SceneManager.GetSceneAt (0).name, SceneManager.sceneCount);
ClientDebugUI.i.Log (_debugString);
Debug.Log (_debugString);
}
if (SceneManager.GetSceneAt(0).name == lobbyScene)
{
if (topPanel.isInGame)
{
ChangeTo(lanPanel);
if (_isMatchmaking)
{
if (conn.playerControllers[0].unetView.isServer)
{
backDelegate = StopHostClbk;
}
else
{
backDelegate = StopClientClbk;
}
}
else
{
if (conn.playerControllers[0].unetView.isClient)
{
backDelegate = StopHostClbk;
}
else
{
backDelegate = StopClientClbk;
}
}
}
else
{
ChangeTo(mainMenuPanel);
}
topPanel.ToggleVisibility(true);
topPanel.isInGame = false;
}
else
{
_debugString = string.Format ("LobbyManager.OnLobbyClientSceneChanged: scene at 0={0} (sceneCount={1})",
SceneManager.GetSceneAt(0).name, SceneManager.sceneCount);
//ClientDebugUI.i.Log (_debugString, GameColor.Black);
//Debug.Log (_debugString.Colorize(GameColor.Yellow));
ChangeTo(null);
//Destroy(GameObject.Find("MainMenuUI(Clone)")); // QUESTIION: why?
//backDelegate = StopGameClbk;
topPanel.isInGame = true;
topPanel.ToggleVisibility(false);
}
}
public override void OnLobbyClientAddPlayerFailed()
{
float bonus = 0.0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnLobbyClientAddPlayerFailed: +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
base.OnLobbyClientAddPlayerFailed ();
}
// End-of-LobbyNetworkManager overrides III:
// --------
// NetworkManager overrides I:
public override NetworkClient StartHost(ConnectionConfig config, int maxConnections)
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.StartHost (a): +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
return base.StartHost (config, maxConnections);
}
public override NetworkClient StartHost(MatchInfo info)
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.StartHost (b): +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
return base.StartHost (info);
}
public override NetworkClient StartHost()
{
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.StartHost (c): +{0} ({1})", bonus, autoMatch.timeout.ToString("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
return base.StartHost ();
}
public override void OnClientError(NetworkConnection conn, int errorCode)
{
//base.OnClientError (conn, errorCode); // empty viretual stub
float bonus = 0f;
autoMatch.AddTimeout (bonus);
if (_debugAll) {
_debugString = string.Format ("LobbyManager.OnClientError: errorCode={0} (bonus time={1})", errorCode, bonus);
ClientDebugUI.i.Log (_debugString, GameColor.Red);
}
ChangeTo(mainMenuPanel);
infoPanel.Display("Cient error : " + (errorCode == 6 ? "timeout" : errorCode.ToString()), "Close", null);
}
public override void OnClientNotReady (NetworkConnection conn)
{
//base.OnClientNotReady (conn); // empty virtual stub
float bonus = 0f;
autoMatch.AddTimeout (bonus);
_debugString = string.Format ("LobbyManager.OnClientNotReady: +{0} ({1})", bonus, autoMatch.timeout.ToString ("0.00"));
if (_debugAll) {
ClientDebugUI.i.Log (_debugString, GameColor.Blue);
Debug.Log (_debugString);
}
}
public override void OnMatchCreate(bool success, string extendedInfo, MatchInfo matchInfo)
{
base.OnMatchCreate(success, extendedInfo, matchInfo); // if 'success' is true, calls NetworkManager.StartHost(matchInfo);
// NOTE: in earlier version of the Network Meteoroid example (from which the majority of
// the lobby/match-making code is copied), cast was applied as (ulong)matchInfo.networkId
_currentMatchID = (System.UInt64)matchInfo.networkId;
// register custom message with the server
NetworkServer.RegisterHandler(CustomMessage.SetParent, OnSetParent); // TODO, test if it's necessary
}
public override void OnDestroyMatch (bool success, string extendedInfo)
{
base.OnDestroyMatch (success, extendedInfo); // debug log only
if (_disconnectServer)
{
StopMatchMaker();
StopHost();
}
}
// End-of-NetworkManager overrides I:
public void ChangeTo(RectTransform newPanel)
{
if (currentPanel != null)
{
currentPanel.gameObject.SetActive(false);
}
if (newPanel != null)
{
newPanel.gameObject.SetActive(true);
}
currentPanel = newPanel;
if (currentPanel != mainMenuPanel)
{
backButton.gameObject.SetActive(true);
}
else
{
//backButton.gameObject.SetActive(false);
backDelegate = () => GoHome();
SetServerInfo("Offline", "None");
_isMatchmaking = false;
}
}
public void DisplayIsConnecting()
{
var _this = this;
infoPanel.Display("Connecting...", "Cancel", () => { _this.backDelegate(); });
infoPanel.singleButton.interactable = !autoMatch.autoMatchToggle.isOn;
}
public void SetServerInfo(string status, string host)
{
statusInfo.text = status;
hostInfo.text = host;
}
public void GoBackButton()
{
if (backDelegate == null) {
_debugString = string.Format ("LobbyManager.GoBackButton: backDelegate is null, aborting", "");
ClientDebugUI.i.Log (_debugString, GameColor.Red);
Debug.LogWarning (_debugString);
} else {
backDelegate ();
}
}
public void AddLocalPlayer()
{
TryToAddPlayer();
}
public void RemovePlayer(LobbyPlayer player)
{
player.RemovePlayer();
}
public void GoMainMenuClbk()
{
ChangeTo(mainMenuPanel);
}
public void StopHostClbk()
{
if (_isMatchmaking)
{
if(matchMaker != null)
{
matchMaker.DestroyMatch((NetworkID)_currentMatchID, 0, OnDestroyMatch); // WARNING, HARDCODE-ing domain value to 0
}
_disconnectServer = true;
}
else
{
StopHost();
}
ChangeTo(mainMenuPanel);
}
public void StopClientClbk()
{
StopClient();
if (_isMatchmaking)
{
StopMatchMaker();
}
ChangeTo(mainMenuPanel);
}
public void StopServerClbk()
{
StopServer();
ChangeTo(mainMenuPanel);
}
public void KickPlayer(NetworkConnection conn)
{
conn.Send(_msgKicked, new KickMsg());
}
public void KickedMessageHandler(NetworkMessage netMsg)
{
infoPanel.Display("Kicked by Server", "Close", null);
netMsg.conn.Disconnect();
}
//allow to handle the (+) button to add/remove player
public void OnPlayersNumberModified(int count)
{
_playerNumber += count;
int localPlayerCount = 0;
foreach (PlayerController p in ClientScene.localPlayers)
localPlayerCount += (p == null || p.playerControllerId == -1) ? 0 : 1;
addPlayerButton.SetActive(localPlayerCount < maxPlayersPerConnection && _playerNumber < maxPlayers);
}
public IEnumerator ServerCountdownCoroutine()
{
float remainingTime = prematchCountdown;
int floorTime = Mathf.FloorToInt(remainingTime);
while (remainingTime > 0)
{
yield return null;
remainingTime -= Time.deltaTime;
int newFloorTime = Mathf.FloorToInt(remainingTime);
if (newFloorTime != floorTime)
{//to avoid flooding the network of message, we only send a notice to client when the number of plain seconds change.
floorTime = newFloorTime;
for (int i = 0; i < lobbySlots.Length; ++i)
{
//there is maxPlayer slots, so some could be == null, need to test it before accessing!
if (lobbySlots[i] != null)
{
(lobbySlots[i] as LobbyPlayer).RpcUpdateCountdown(floorTime);
}
}
}
}
for (int i = 0; i < lobbySlots.Length; ++i)
{
if (lobbySlots[i] != null)
{
(lobbySlots[i] as LobbyPlayer).RpcUpdateCountdown(0);
}
}
ServerChangeScene(playScene);
}
public void GoHome()
{
Debug.Log("LobbyManager.GoHome()".Colorize(GameColor.Red));
StartCoroutine (StopNetwork ());
}
IEnumerator StopNetwork()
{
if (NetworkServer.active)
StopHost ();
if(NetworkClient.active)
StopClient ();
yield return new WaitForSeconds (1f); // HACK
SceneManager.LoadSceneAsync("home");
}
void OnLevelFinishedLoading(Scene scene, LoadSceneMode mode)
{
if (scene.name == "battle")
{
// clean up the lobby in-case we return there due to a network failuer (e.g. vs. loading a different 'home' scene at the successful conclusion of a battle)
//DestroyLobbyPlayers(); // NOTE: this is not a safe way to 'clean up' the lobby, causes null ref exception in NetworkLobbyMnager.SceneLoadedForPlayer
}
}
void DestroyLobbyPlayers()
{
var list = lanPanel.GetComponent<LobbyPlayerList> ().playerListContentTransform;
for (int i = list.childCount-1; i >= 0; i--) {
Object.Destroy (list.GetChild (i).gameObject);
}
}
// -------- AMM
// LAN: start host
public void StartLANHost ()
{
if (_debugAll) {
_debugString = string.Format ("LobbyManager.StartLANHost: timeout={0}", autoMatch.timeout.ToString ("0.00"));
ClientDebugUI.i.Log (_debugString, GameColor.Green);
}
// NOTE: below line calls NetworkManager.StartHost (https://goo.gl/cmqjBi), which calls empty the stub function
// NetworkManager.OnStartHost. NetworkManager.OnStartHost is overridden in NetworkLobbyManager (https://goo.gl/2cgIPE)
// and calls empty stub function NetworkLobbyManager.OnLobbyStartHost which we override below! If the return value
// is null, there was a problem starting the server so
NetworkClient netClient = StartHost ();
if (netClient == null)
{
// shut down immediatly
_debugString = string.Format ("LobbyManager.StartLANHost: StartHost () was null!", "");
ClientDebugUI.i.Log (_debugString, GameColor.Red);
}
}
// LAN: stop host
public void StopLANHost ()
{
if (_debugAll) {
_debugString = string.Format ("LobbyManager.StopLANHost: timeout={0}", autoMatch.timeout.ToString ("0.00"));
ClientDebugUI.i.Log (_debugString, GameColor.Red);
}
StopHostClbk();
}
// LAN: start (remote) client search for game
public void ListLANGames()
{
if (_debugAll) {
_debugString = string.Format ("LobbyManager.ListLANGames: timeout={0}", autoMatch.timeout.ToString ("0.00"));
ClientDebugUI.i.Log (_debugString, GameColor.Green);
}
LobbyManager.s_Singleton.ChangeTo(lanPanel);
LobbyManager.s_Singleton.networkAddress = ipInput.text;
// LINKS: NetworkManager.cs (https://goo.gl/cmqjBi), NetworkLobbyManager.cs (https://goo.gl/2cgIPE)
// NOTE: StartClient refers to LobbyManager : NetworkLobbyManager : NetworkManager.StartClient() which
// does a bunch of HLAPI initialization before calling OnStartClient(), an empty virtual stub in
// NetworkManager. OnStartClient is, however, overridden in NetworkLobbyManager which handles registration
// of lobby player prefab as well as message handlers for MsgType.LobbyReadyToBegin (OnClientReadyToBegin)
// and MsgType.LobbyAddPlayerFailed (OnClientAddPlayerFailedMessage). The final call in
// NetworkLobbyManager.OnStartClient is to OnLobbyStartClient, an empty virtual stub (not overridden by default)
//NetworkClient lobbyClient = (next line)
LobbyManager.s_Singleton.StartClient();
//lobbyClient.RegisterHandler(MsgType.LobbyReadyToBegin, OnClientReadyToBegin); // AMM test
LobbyManager.s_Singleton.backDelegate = LobbyManager.s_Singleton.StopClientClbk;
LobbyManager.s_Singleton.DisplayIsConnecting ();
LobbyManager.s_Singleton.SetServerInfo ("Connecting...", LobbyManager.s_Singleton.networkAddress);
}
// LAN: stop (remote) client search for game
public void CloseLANGames()
{
if (_debugAll) {
_debugString = string.Format ("LobbyManager.CloseLANGames: {0}", "");
ClientDebugUI.i.Log (_debugString, GameColor.Red);
}
infoPanel.gameObject.SetActive (false);
LobbyManager.s_Singleton.StopClientClbk ();
}
// End-of-LAN
// MM: start host
public void StartMatch ()
{
if (_debugAll) {
_debugString = string.Format ("LobbyManager.StartMatch: timeout={0}", autoMatch.timeout.ToString ("0.00"));
ClientDebugUI.i.Log (_debugString, GameColor.Green);
}
LobbyManager.s_Singleton.StartMatchMaker ();
// HARDCODE, LINK: http://docs.unity3d.com/540/Documentation/ScriptReference/Networking.Match.NetworkMatch.CreateMatch.html
LobbyManager.s_Singleton.matchMaker.CreateMatch (
matchNameInput.text,
(uint)LobbyManager.s_Singleton.maxPlayers,
true,
"",
"",
"",
0,
0,
LobbyManager.s_Singleton.OnMatchCreate);
LobbyManager.s_Singleton.backDelegate = LobbyManager.s_Singleton.StopHost;
LobbyManager.s_Singleton._isMatchmaking = true;
LobbyManager.s_Singleton.DisplayIsConnecting ();
LobbyManager.s_Singleton.SetServerInfo ("Matchmaker Host", LobbyManager.s_Singleton.matchHost);
}
// MM: stop host
public void StopMatch ()
{
if (_debugAll) {
_debugString = string.Format ("LobbyManager.StopMatch: {0}", "");
ClientDebugUI.i.Log (_debugString, GameColor.Red);
}
StopHost();
}
// MM: start (remote) client search for game
public void ListMatches()
{
if (_debugAll) {
_debugString = string.Format ("LobbyManager.ListMatches: timeout={0}", autoMatch.timeout.ToString ("0.00"));
ClientDebugUI.i.Log (_debugString, GameColor.Green);
}
StartMatchMaker();
backDelegate = LobbyManager.s_Singleton.GoMainMenuClbk;
ChangeTo(mmServerPanel);
}
// MM: stop (remote) client search for game
public void CloseMatches()
{
if (_debugAll) {
_debugString = string.Format ("LobbyManager.CloseMatches: {0}", "");
ClientDebugUI.i.Log (_debugString, GameColor.Red);
}
GoMainMenuClbk ();
}
// End-of-Matchmaker AMM
void OnSetParent(NetworkMessage netMsg)
{
SetParentMessage msg = netMsg.ReadMessage<SetParentMessage>();
if (!ClientScene.objects.ContainsKey (msg.netId)) {
_debugString = string.Format ("LobbyManager.OnSetParent: client scene (ready={0}) doesn't contain netId {1}, aborting", ClientScene.ready, msg.netId);
Debug.Log (_debugString);
ClientDebugUI.i.Log (_debugString, GameColor.Red);
return;
}
if (!ClientScene.objects.ContainsKey (msg.parentNetId)) {
_debugString = string.Format ("LobbyManager.OnSetParent: client scene (ready={0}) doesn't contain parent netId {1}, aborting", ClientScene.ready, msg.parentNetId);
Debug.Log (_debugString);
ClientDebugUI.i.Log (_debugString, GameColor.Red);
return;
}
ClientScene.objects[msg.netId].transform.parent = ClientScene.objects[msg.parentNetId].transform;
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.