Search Unity

  1. Welcome to the Unity Forums! Please take the time to read our Code of Conduct to familiarize yourself with the forum rules and how to post constructively.
  2. We have updated the language to the Editor Terms based on feedback from our employees and community. Learn more.
    Dismiss Notice
  3. Join us on November 16th, 2023, between 1 pm and 9 pm CET for Ask the Experts Online on Discord and on Unity Discussions.
    Dismiss Notice

Photon Setting Players to Random Factions

Discussion in 'Scripting' started by Camronas, Sep 7, 2015.

  1. Camronas

    Camronas

    Joined:
    Apr 20, 2012
    Posts:
    154
    Hey guys;

    I am trying to make a multiplayer game where everyone but one person are part of a team. I am trying to pick that player at random.
    This has been very difficult because I can't seem to access anyone's variables directly. I have thought about doing this several ways but nothing seems to work.

    I started by having the Master generate a random number, then do a loop to see who's index matched. I couldn't seem to access the index and or the faction number.

    I was also thinking about doing an RPC call to choose a random one; the issue is that then I can't guarantee that only 1 person will be on team B. And again without being able to see everyone's variables I can't double check for duplicates.

    I am really lost with this :\ Any help would be great!
     
  2. Camronas

    Camronas

    Joined:
    Apr 20, 2012
    Posts:
    154
    Here is the latest plan:


    Code (CSharp):
    1. void SpawnMyPlayer()
    2.     {
    3.         SpawnSpotScript[] spots = GameObject.FindObjectsOfType<SpawnSpotScript>();
    4.  
    5.         SpawnSpotScript mySpawnSpot = spots [Random.Range (0, spots.Length)];
    6.  
    7.         MenuCamera.SetActive (false);
    8.         GameObject myPlayerOB = (GameObject)(PhotonNetwork.Instantiate("PlayerCharacter", mySpawnSpot.transform.position, Quaternion.identity, 0));
    9.         factionID = mySpawnSpot.GetComponent<SpawnSpotScript> ().factionID;
    10.         ((MonoBehaviour)myPlayerOB.GetComponent ("Platformer2DUserControl")).enabled = true;
    11.         ((MonoBehaviour)myPlayerOB.GetComponent ("PlatformerCharacter2D")).enabled = true;
    12.         ((MonoBehaviour)myPlayerOB.GetComponent ("RoomManager")).enabled = true;
    13.         myPlayerOB.gameObject.tag = "Player";
    14.         myPlayerOB.transform.FindChild("PlayerCamera").gameObject.SetActive(true);
    15.  
    16.         if (factionID == 0)
    17.         {
    18.             myPlayerOB.GetComponent<SpriteRenderer>().color = Color.red;
    19.         }
    20.         if (factionID == 1)
    21.         {
    22.             myPlayerOB.GetComponent<SpriteRenderer>().color = Color.blue;
    23.         }
    24.     }
    The players each spawn at spawn points, the spawn point can assign their faction/team. Question is, how can I make a player unable to spawn at an already used spawn point? All of my players spawn at the same time which is making it harder to turn spawn points on or off.

    Any help would be very welcome!
     
  3. Camronas

    Camronas

    Joined:
    Apr 20, 2012
    Posts:
    154
    I am really at a loss with this, does anyone have any ideas?

    The best I could come up with at the moment is to do this:

    Code (CSharp):
    1. public void StartGame()
    2.     {
    3.         if (PhotonNetwork.isMasterClient)
    4.         {
    5.             int enemyPlayer = Random.Range(0, PhotonNetwork.playerList.Length);
    6.            
    7.             GetComponent<PhotonView>().RPC("MakePlayerEvil_RPC", PhotonNetwork.playerList[enemyPlayer]);
    8.         }
    9.  
    10.         GetComponent<PhotonView>().RPC("StartGame_RPC", PhotonTargets.All);
    11.     }
    12.  
    13.     [PunRPC]
    14.     void MakePlayerEvil_RPC()
    15.     {
    16.         int factionID = 1;
    17.     }
    18.  
    From my understanding the "Master Client" should only be the one player. The pick a random number/player and send that player a message to do a function. That function sets their faction to be 1 rather than 0 like everyone else. Sadly this doesn't work.

    Can anyone explain this too me? I really don't know what to do.
     
    LoudCorp-Games likes this.
  4. justoon

    justoon

    Joined:
    Nov 7, 2013
    Posts:
    9
    Hi

    Your latest idea looks like it has some promise. When you say it's not working, what specifically isn't working?

    Keep in mind that RPC calls are made on every client, so you would need some way of differentiating them.
    Perhaps as players join the game, they get an id assigned to them and you can check this id in the RPC and if it matches then assign that matches player the evil faction.
     
  5. Camronas

    Camronas

    Joined:
    Apr 20, 2012
    Posts:
    154
    Well, I assumed that the:

    Code (CSharp):
    1. if (PhotonNetwork.isMasterClient)
    Would have the master choose a random number.

    Code (CSharp):
    1. int enemyPlayer = Random.Range(0, PhotonNetwork.playerList.Length);
    The random number would be relevant to the number of players in the room.

    Code (CSharp):
    1. GetComponent<PhotonView>().RPC("MakePlayerEvil_RPC", PhotonNetwork.playerList[enemyPlayer]);
    When making an RPC call it says you can send it to specific players so I was hoping to use player list and the random number send the message only to the player with that index.
    That was the plan anyway.
    In the spawn function they come in with a red or blue material based on their faction; they always come in with red which is faction 0. So I know no one is being set to faction 1.
     
  6. justoon

    justoon

    Joined:
    Nov 7, 2013
    Posts:
    9
    Overall, I think the logical flow makes sense.
    It maybe a question of timing - I see in your Spawn function you're checking the assigned factionId and in the RPC you are assigning the factionId. Put breakpoints in these two areas and validate if
    1. your random player is receiving the RPC call
    2. you are assigning the factionId before reading it
     
  7. Camronas

    Camronas

    Joined:
    Apr 20, 2012
    Posts:
    154
    I did a break point and changed my code slightly just to make absolutely sure:


    Code (CSharp):
    1. public void StartGame()
    2.     {
    3.         if (PhotonNetwork.isMasterClient)
    4.         {
    5.             int enemyPlayer = Random.Range(0, PhotonNetwork.playerList.Length);
    6.            
    7.             GetComponent<PhotonView>().RPC("MakePlayerEvil_RPC", PhotonNetwork.playerList[enemyPlayer]);
    8.         }
    9.     }
    10.  
    11.     [PunRPC]
    12.     void MakePlayerEvil_RPC()
    13.     {
    14.         int factionID = 1;
    15.         GetComponent<PhotonView>().RPC("StartGame_RPC", PhotonTargets.All);
    16.     }
    17.  
    18.     [PunRPC]
    19.     void StartGame_RPC()
    20.     {
    21.         inRoomLobby = false;
    22.         this.StartCoroutine(this.MoveToGameScene());
    23.     }
    24.  
    The break point triggers on "int factionID = 1;" which means it is getting there and should set the factionID to 1 therefore spawning as Blue rather than Red.
    I put the "GetComponent<PhotonView>().RPC("StartGame_RPC", PhotonTargets.All);" inside that function as well; only the "Evil" player should be able to access this function at all and therefore must have it's ID set before telling everyone to start the game fully.

    Despite the break point and the safety net they all still spawn in as Red and non are Blue.
     
  8. Camronas

    Camronas

    Joined:
    Apr 20, 2012
    Posts:
    154
    NEVERMIND! God I feel so dumb right now.

    Code (CSharp):
    1.     [PunRPC]
    2.     void MakePlayerEvil_RPC()
    3.     {
    4.         int factionID = 1;
    5.         GetComponent<PhotonView>().RPC("StartGame_RPC", PhotonTargets.All);
    6.     }
    Should be:

    Code (CSharp):
    1.     [PunRPC]
    2.     void MakePlayerEvil_RPC()
    3.     {
    4.         factionID = 1;
    5.         GetComponent<PhotonView>().RPC("StartGame_RPC", PhotonTargets.All);
    6.     }
    I was declaring it again rather than using the one I had already made.

    Cheers for all the help! You really got me to look at this in a much better way!