Search Unity

Resolved How to crate/join a host with a variable and access it in player script OnNetworkSpawn method

Discussion in 'Netcode for GameObjects' started by lobador, Nov 17, 2022.

  1. lobador

    lobador

    Joined:
    May 29, 2020
    Posts:
    13
    Let's say I have Two Buttons:

    Play as Blue Player

    Play as Red Player


    The player clicked the "Play as Blue Player" button and I started the host with the Blue parameter;
    NetworkManager.Singleton.StartHost();


    If the next player clicks the "Play as Red Player", it can connect the created host.
    NetworkManager.Singleton.StartClient();

    Otherwise, I need to create a new host with a Red parameter.

    and I need to know which player is red or blue in the player script OnNetworkSpawn method.

    I hope I have achieved to explain my issue :)

    Thanks in advance!
     
  2. CodeSmile

    CodeSmile

    Joined:
    Apr 10, 2014
    Posts:
    5,998
    I wouldn‘t do it that way. Let one player be the host, the other a client. That‘s one choice. This should be independent of the choice of color. So first player chooses host, second player chooses connect. Host can choose its color, client automatically uses the other color and has no choice in it (host privilege).
     
  3. lobador

    lobador

    Joined:
    May 29, 2020
    Posts:
    13
    Hi @CodeSmile thank you so much for your answer but I think I wasn't clear enough.

    I want to create one to one match.
    Let's say Attack and Defence instead of Red and Blue.

    if one player creates an attacking host, only a player who wants to defence should join this host. Otherwise, if the second player selects the attack, it should create a new host instead of joining the previous host.

    I hope I have explained my requirement more clearly this time :)
     
  4. RikuTheFuffs-U

    RikuTheFuffs-U

    Unity Technologies

    Joined:
    Feb 20, 2020
    Posts:
    440
    Hey @lobador , as CodeSMile said, these are 2 different choices.

    What I'd recommend to do is:

    1. Make one player start as a host, and the other as a client
    2. Once both players are connected to the game, they pick the role (attack or defense). The fastest player gets the role they want, and the other one gets what is left.
    3. At the end of the match, you swap the roles and make the players play the other one.

    Alternatively, you can use a matchmaker service that lets players choose whether they want to play as an "attacker" or "defender" before connecting to anybody else. This solves the root problem
     
  5. lobador

    lobador

    Joined:
    May 29, 2020
    Posts:
    13
    Hi @RikuTheFuffs-U thanks for your answer. I think this is what I need. Is there any sample or nice tutorial for the matchmaker service that you know?

    Thanks in advance!
     
  6. RikuTheFuffs-U

    RikuTheFuffs-U

    Unity Technologies

    Joined:
    Feb 20, 2020
    Posts:
    440
    @lobador Sure! There's the official documentation, which also provides a code sample. All the configuration is done through the Unity dashboard, and it's pretty easy to set up (I use it myself in a production project, together with Multiplay/Game Server Hosting for Dedicated Servers).
    You can also read more about the matchmaker service here to see if it's really what you're looking for (it probably is!)
     
    lobador likes this.
  7. lobador

    lobador

    Joined:
    May 29, 2020
    Posts:
    13
    Thank you so much!
     
    RikuTheFuffs-U likes this.
  8. CosmoM

    CosmoM

    Joined:
    Oct 31, 2015
    Posts:
    204
    The way I do it is that players select their team on the login screen, which is then sent on the payload. In the approval check the server then checks whether the team choice is (still) valid.

    A code snippet for sending the payload:
    Code (CSharp):
    1. string payload=JsonUtility.ToJson(new ConnectionPayload(playerTeam,playerName,Application.version));
    2. byte[] payloadBytes=System.Text.Encoding.UTF8.GetBytes(payload);
    3. NetworkManager.Singleton.NetworkConfig.ConnectionData=payloadBytes; //would make sense to add password to this
    4. NetworkManager.Singleton.StartClient();
    And checking the payload in the approval check (note that ClientDataManager is a custom class that exists only for the server):
    Code (CSharp):
    1. ConnectionPayload payload=JsonUtility.FromJson<ConnectionPayload>(System.Text.Encoding.ASCII.GetString(connectionData));
    2. if (!Application.version.Equals(payload.gameVersion,System.StringComparison.Ordinal)) {
    3.     Debug.Log("Version mismatch!");
    4.     approveConnection=false;
    5. } //if
    6. else if (ClientDataManager.instance.NameIsInUse(payload.playerName)) {
    7.     Debug.Log("Client name ("+payload.playerName+") is already being used!");
    8.     approveConnection=false;
    9. } //if
    10. else if (ClientDataManager.instance.TeamIsFull(payload.playerTeam)) {
    11.     Debug.Log("Client team ("+payload.playerTeam+") is already full!");
    12.     approveConnection=false;
    13. } //else if
    14. else {
    15.     ClientDataManager.instance.AddClientData(clientId,payload.playerTeam,payload.playerName);
    16. } //else
     
    lobador likes this.
  9. lobador

    lobador

    Joined:
    May 29, 2020
    Posts:
    13
    Hey @CosmoM this very looks like what I needed. I will check this tomorrow as far as I can. Thank you so much!