Version: 2019.2
プレイヤーゲームオブジェクト
ゲームオブジェクトのスポーン (spawn)

カスタムのプレイヤースポーン (Spawning)

ノート: UNet は非推奨となり、今後 Unity から削除される予定です。新しいシステムが開発中です。詳細は ブログFAQ を参照してください。

Network Manager にはビルトインの基本的なプレイヤーのスポーン機能が備わっています。ただし、例えば、新しく生成するプレイヤーに色を指定するなど、プレイヤーのスポーンの処理にカスタマイズが必要な場合があります。

これを行うには、Network Manager のデフォルトの挙動を独自のスクリプトでオーバーライドする必要があります。

When the Network Manager adds a player, it also instantiates a GameObject from the Player Prefab and associates it with the connection. To do this, the Network Manager calls NetworkServer.AddPlayerForConnection. You can modify this behaviour by overriding NetworkManager.OnServerAddPlayer. The default implementation of OnServerAddPlayer instantiates a new player instance from the player Prefab and calls NetworkServer.AddPlayerForConnection to spawn the new player instance. Your custom implementation of OnServerAddPlayer must also call NetworkServer.AddPlayerForConnection, but you are free to perform any other initialization you require in that method too.

以下の例では、プレイヤーの色をカスタマイズします。 まず、プレイヤープレハブに色のスクリプトを加えます。

using UnityEngine;
using UnityEngine.Networking;
class Player : NetworkBehaviour
{
    [SyncVar]
    public Color color;
}

Next, create a NetworkManager to handle spawning.

using UnityEngine;
using UnityEngine.Networking;
public class MyNetworkManager : NetworkManager
{
    public override void OnServerAddPlayer(NetworkConnection conn, short playerControllerId)
    {
        GameObject player = (GameObject)Instantiate(playerPrefab, Vector3.zero, Quaternion.identity);
        player.GetComponent<Player>().color = Color.red;
        NetworkServer.AddPlayerForConnection(conn, player, playerControllerId);
    }
}

NetworkServer.AddPlayerForConnection 関数は OnServerAddPlayer 内から呼び出される必要はありません。正しい接続のオブジェクトと playerControllerId が渡されている限り、OnServerAddPlayer が返された後に呼び出されます。これにより、リモートデータソースからプレイヤーデータをロードするなど、非同期ステップの発生を可能にします。

ほとんどのマルチプレイヤーゲームでは、通常、クライアントごとに 1 プレイヤーが必要ですが、HLAPI はプレイヤーとクライアントを別々の概念として扱います。なぜなら、ある場合では (例えば、複数のコントローラーが 1 つのコンソールシステムに接続している場合)、1 つの接続で複数のプレイヤーゲームオブジェクトが必要な場合があるからです。1 つの接続に対して複数のプレイヤーが存在する場合、 playerControllerId プロパティーを使ってそれぞれを区別します。この識別子は接続に関連していて、プレイヤーに関連するコントローラーの ID をクライアントにマッピングします。

The system automatically spawns the player GameObject passed to NetworkServer.AddPlayerForConnection on the server, so you don’t need to call NetworkServer.Spawn for the player. Once a player is ready, the active networked GameObjects (that is, GameObjects with an associated NetworkIdentity) in the Scene spawn on the player’s client. All networked GameObjects in the game are created on that client with their latest state, so they are in sync with the other participants of the game.

You don’t need to use playerPrefab on the NetworkManager to create player GameObjects. You could use different methods of creating different players.

準備完了の状態

In addition to players, client connections also have a “ready” state. The host sends clients that are ready information about spawned GameObjects and state synchronization updates; clients which are not ready are not sent these updates. When a client initially connects to a server, it is not ready. While in this non-ready state, the client can do things that don’t require real-time interactions with the game state on the server, such as loading Scenes, allowing the player to choose an avatar, or fill in log-in boxes. Once a client has completed all its pre-game work, and all its Assets are loaded, it can call ClientScene.Ready to enter the “ready” state. The simple example above demonstrates implementation of ready states; because adding a player with NetworkServer.AddPlayerForConnection also puts the client into the ready state if it is not already in that state.

クライアントは準備完了していなくてもネットワークメッセージを送信、受信することができます。つまり、アクティブなプレイヤーゲームオブジェクト無しに、そうすることが可能だということを意味しています。そのため、クライアントはメニューや選択スクリーンで、プレイヤーオブジェクトが存在しないにも関わらずゲームへと接続し、相互作用することができます。コマンドや RPC 呼び出しを使用しないメッセージの送信に関する詳細は、ネットワークメッセージ を参照してください。

プレイヤーの切り替え

To replace the player GameObject for a connection, use NetworkServer.ReplacePlayerForConnection. This is useful for restricting the commands that players can issue at certain times, such as in a pre-game lobby screen. This function takes the same arguments as AddPlayerForConnection, but allows there to already be a player for that connection. The old player GameObject does not have to be destroyed. The NetworkLobbyManager uses this technique to switch from the NetworkLobbyPlayer GameObject to a gameplay player GameObject when all the players in the lobby are ready.

また、ゲームオブジェクトを破棄した後に、ReplacePlayerForConnection を使用してプレイヤーを再生成することができます。場合によっては、単にゲームオブジェクトを無効にして、そのゲーム属性を再生成にするほうが良い場合があります。以下のコードサンプルは、実際に、破棄したゲームオブジェクトを新しいゲームオブジェクトで置き換える方法を示しています。

class GameManager
{
    public void PlayerWasKilled(Player player)
    {
        var conn = player.connectionToClient;
        var newPlayer = Instantiate<GameObject>(playerPrefab);
        Destroy(player.gameObject);
        NetworkServer.ReplacePlayerForConnection(conn, newPlayer, 0);
    }
}

プレイヤーゲームオブジェクトの接続が断たれると、クライアントはコマンドを実行できなくなります。ただし、ネットワークメッセージは送信することができます。

To use ReplacePlayerForConnection you must have the NetworkConnection GameObject for the player’s client to establish the relationship between the GameObject and the client. This is usually the property connectionToClient on the NetworkBehaviour class, but if the old player has already been destroyed, then that might not be readily available.

To find the connection, there are some lists available. If using the NetworkLobbyManager, then the lobby players are available in lobbySlots. The NetworkServer also has lists of connections and localConnections.

プレイヤーゲームオブジェクト
ゲームオブジェクトのスポーン (spawn)