- Home /
How do I keep values synchronized over the Photon Network?
Hello! I am trying to write a basic matchmaking script where players can create or join a room, and then once there, the player joins a team. This is the issue. I use a combo of PhotonNetwork player customProperties and some variables in the script to assign a team and store the team in the player. I can't seem to keep the variables "redTeamPlayers" and "blueTeamPlayers" in sync with every client, resulting every client to join red team. Please help me come up with a solution to this problem.
Here are a few scripts and background info you should know...
-There are 2 scenes
-login
-matchmaking
-Each one has a script
-loginArea (Where properties and connections are set up)
-tempMatchSystem(Where the magic/meat of the app happens)
-The only plugin needed for this to work is Photon Unity Networking
LoginArea script
using UnityEngine;
using System.Collections;
using Hashtable = ExitGames.Client.Photon.Hashtable;
public class loginArea : Photon.MonoBehaviour {
private string userName = " "; //user and pass fields
private string passWord = " ";
private Rect loginRect = new Rect(Screen.width/2-200,Screen.height/2-100, 400,200); //Size of login screen
public Color defaultColor = Color.white;
public string gameVersion = "t01";
public GUISkin skin;
//Photon Initialization
Hashtable h;
//Lerp action
private float rectMove1 = 0f;
private float rectMove2 = 0f;
private bool isDoneLerping = false;
void Start () {
PhotonNetwork.ConnectUsingSettings(gameVersion);
h = new Hashtable(10);
h.Add("Ship",0);
PhotonNetwork.player.SetCustomProperties(h);
Debug.Log(PhotonNetwork.player.customProperties);
}
void Update () {
rectMove1 = Mathf.Lerp(rectMove1,400,Time.fixedDeltaTime * 0.5f);
rectMove2 = Mathf.Lerp(rectMove2,200,Time.fixedDeltaTime * 0.5f);
loginRect = new Rect(Screen.width/2-200,Screen.height/2-100,rectMove1,rectMove2);
if (rectMove1 >= 380) {
isDoneLerping = true;
}
}
void OnGUI () {
GUI.skin = skin;
GUI.Window(0,loginRect,LoginWindow,"Login");
}
public void LoginWindow (int id) {
GUI.skin = skin; //Set the skin as the correct GUI skin.
if(!isDoneLerping) {
return;
}
if(PhotonNetwork.connected) {
GUI.contentColor = Color.green;
GUILayout.Label("Server: Online"); //make green online
GUI.contentColor = defaultColor;
}
else {
GUI.contentColor = Color.red;
GUILayout.Label("Server: Failed"); //Make red offline
GUI.contentColor = defaultColor;
}
GUILayout.BeginHorizontal();
GUILayout.Label("Username:");
userName = GUILayout.TextField(userName,16); //Username field, and it will look like (Label, Textfield)
GUILayout.EndHorizontal();
GUILayout.BeginHorizontal();
GUILayout.Label("Password:");
passWord = GUILayout.PasswordField(passWord,'*',16); //Hide the password so others can't see!
GUILayout.EndHorizontal();
GUILayout.Space(70f);
GUILayout.BeginHorizontal();
if (PhotonNetwork.connectedAndReady) {
if (GUILayout.Button("Login")) {
//TODO make this dynamic using Combu
PhotonNetwork.playerName = userName;
Application.LoadLevel(1);
}
}
if (GUILayout.Button("Exit")) { //If the player exits..
//TODO Make this dynamic via Combu
PhotonNetwork.Disconnect(); //Disconnect, but don't abruptly quit!
}
GUILayout.EndHorizontal();
}
void OnDisconnectedFromPhoton () {
Application.Quit();//End the session once it's wrapped up.
}
}
tempMatchSystem script
using System.Collections;
public class tempMatchSystem : Photon.MonoBehaviour {
//Teams Controller
public int redTeamPlayers = 0;
public int blueTeamPlayers = 0;
private int localBluePlayers = 0;
private int localRedPlayers = 0;
//matchmaking stuff
private RoomInfo[] rooms;
private PhotonPlayer[] players;
//Temp Strings
private string tempCreateName = "";
//gui stuff
private Rect screenRect = new Rect (Screen.width/2-200,Screen.height/2-200,400,400);
public GUISkin skin;
public Color defaultColor = Color.white;
//Data stuff/Networking
private PhotonView pv;
void Start () {
pv = GetComponent<PhotonView>();
}
void Update () {
if (PhotonNetwork.inRoom && PhotonNetwork.isMasterClient) {
localRedPlayers = redTeamPlayers;
localBluePlayers = blueTeamPlayers;
pv.RPC ("updateTeamValues",PhotonTargets.All);
}
}
void OnGUI () {
GUI.skin = skin;
rooms = PhotonNetwork.GetRoomList();
if (!PhotonNetwork.inRoom) {
GUILayout.Window(0,screenRect,MatchMakingGUI,"Games");
}
if (PhotonNetwork.inRoom) {
GUILayout.Window(1,screenRect,LobbyGUI,"Lobby");
}
}
void MatchMakingGUI (int id) {
GUI.skin = skin;
GUILayout.Label("Create Game");
tempCreateName = GUILayout.TextField(tempCreateName,32);
if (GUILayout.Button ("Create")) {
PhotonNetwork.CreateRoom(tempCreateName);
}
GUILayout.Space(10);
foreach(RoomInfo roomz in rooms) {
if (GUILayout.Button(roomz.name + " |" + roomz.playerCount + "/" + roomz.maxPlayers + "|")) {
PhotonNetwork.JoinRoom(roomz.name);
}
}
GUI.DragWindow(); //At the end for dragability
}
void LobbyGUI (int id) {
players = PhotonNetwork.playerList;
GUILayout.BeginScrollView(new Vector2(0,10));
foreach(PhotonPlayer player in players) {
int? teamNumb = player.customProperties["Team"] as int?; //This is how we read the object's value
if (teamNumb == 0) {
GUI.contentColor = Color.red;
}
if (teamNumb == 1) {
GUI.contentColor = Color.blue;
}
if (player.name == "DaftDev") {
GUI.backgroundColor = Color.green;
}
GUILayout.Button("|" + player.name + "|");
GUI.color = defaultColor;
GUI.contentColor = defaultColor;
GUI.backgroundColor = defaultColor;
}
GUILayout.EndScrollView();
GUILayout.BeginHorizontal();
if (GUILayout.Button("Main Menu")) {
int? teamNumb = PhotonNetwork.player.customProperties["Team"] as int?;
if (teamNumb == 0) {
pv.RPC("leaveTeam",PhotonTargets.All,0); //Notify users we left a team.
}
if (teamNumb == 1) {
pv.RPC("leaveTeam",PhotonTargets.All,0); //Notify users we left a team.
}
PhotonNetwork.LeaveRoom();
}
if (PhotonNetwork.isMasterClient) {
if (GUILayout.Button("Start")) {
//TODO add a start function
}
}
GUILayout.EndHorizontal();
}
void OnJoinedRoom () {
int caseInt = 0;
//Team Controller
if (redTeamPlayers > blueTeamPlayers) {
caseInt = 0; //Tell the switch to place on blue team
}
if (redTeamPlayers < blueTeamPlayers) {
caseInt = 1;
}
if (redTeamPlayers == blueTeamPlayers) {
caseInt = 2;
}
switch(caseInt) {
//TEAM VALUE: 0 = RED, 1 = BLUE.
case 0:
PhotonNetwork.player.customProperties["Team"] = 0;
pv.RPC ("joinTeam",PhotonTargets.All,0); //Notify everyone that we joined a team
break;
case 1:
PhotonNetwork.player.customProperties["Team"] = 1;
pv.RPC ("joinTeam",PhotonTargets.All,1); //Notify everyone that we joined a team
break;
case 2:
PhotonNetwork.player.customProperties["Team"] = 0;
pv.RPC ("joinTeam",PhotonTargets.All,0); //Notify everyone that we joined a team
break;
}
}
[RPC]
void joinTeam(int team) {
switch(team) {
case 0:
redTeamPlayers++;
break;
case 1:
blueTeamPlayers++;
break;
}
}
[RPC]
void leaveTeam(int team) {
switch(team) {
case 0:
redTeamPlayers--;
break;
case 1:
blueTeamPlayers--;
break;
}
}
[RPC]
void updateTeamValues() {
redTeamPlayers = localRedPlayers;
blueTeamPlayers = localBluePlayers;
}
void OnLeftRoom () {
}
//------------------------------------------------------------------------------------------------
//------------------------------------------------------------------------------------------------
}
I apologize for the lengthy scripts; I put lots of work into them and didn't want to hack and slash them. I hope I provided enough insight. Thanks in advance!
Answer by A3tra3rpi · Jul 25, 2014 at 04:12 PM
Would this help? I use this to sync floats, bools and ints over network:
public void OnPhotonSerializeView(PhotonStream stream, PhotonMessageInfo info) {
if(stream.isWriting) {
stream.SendNext(Health);
}
else {
Health = (float)stream.ReceiveNext();
}
}
Your answer
Follow this Question
Related Questions
Photon Unity Networking: Teams? 2 Answers
Creating a realtime cinema sequence in Unity. 2 Answers
asynchronous sound 0 Answers
synchronize multiple monitor 1 Answer