(Unity 5.1 からは UNET の使用を推奨しています。下記の情報は旧ネットワークシステムのものです。)
Remote Procedure Calls (RPC)はリモートマシンの関数呼び出しを可能にします。RPC 実行は通常の関数の呼び出しと似て簡単ですが、理解すべき重要な違いがいくつかあります。
RPC の引数の数は任に決められますが、使用するネットワーク帯域幅が引数の数と大きさにより増えます。最大のパフォーマンスを得る単に引数の数は最小に抑えるべきです。
通常の関数呼び出しと異なって RPC はリクエストの受け手を示す引数を指定します。一通りすべてのケースをカバーするためいくつか RPC 呼び出しモードが用意されてます。例えば RPC をすべての接続マシンで実行、サーバー単独で実行、コール送信元・あるいは任意のクライアントのみ実行しないなど指定できます。
RPC 呼び出しは通常、あるイベントをゲーム内のクライアントすべてで実行するか、特定の 2 つのグループ間でイベント情報を渡すために使用されますが、工夫して好きなように活用できます。例えば、4 つのクライアントが接続して初めて開始するゲームの場合、そのサーバーは、4 番目のクライアントが接続するとすぐにすべてのクライアントに対し RPC の呼び出しを行います。その結果、ゲームが開始されます。あるプレイヤーのクライアントが、全員に RPC の呼び出しを送信しあるアイテムを手に入れたことを知らせることもできます。サーバーはクライアント接続直後に、あるクライアントに RPC を送信してプレイヤーを初期化し、例えば、プレイヤー番号、生成位置、チームカラーなどを割り当てることができます。クライアントはそれと引き換えにサーバーだけに RPC を送信して、希望のカラーや購入したアイテムなどのスタート時のオプションを提示します。
リモート実行する前に関数は RPC としてマーキングする必要があります。このため関数の前に RPC 属性を示す記号を入れます。
using UnityEngine;
using System.Collections;
public class ExampleScript : MonoBehaviour {
[RPC]
void PrintText (string text)
{
Debug.Log(text);
}
}
C# スクリプトの例
// All RPC calls need the @RPC attribute!
@RPC
function PrintText (text : String)
{
Debug.Log(text);
}
JS スクリプトの例
すべてのネットワーク通信は NetworkView コンポーネントで行うため RPC 関数を宣言したスクリプトに呼び出し前にアタッチする必要があります。
次の変数タイプを RPC の引数として使用できます:
例えば、次のコードによりひとつの string 引数を持つ RPC を実行します:
using UnityEngine;
using UnityEngine.Network;
using System.Collections;
public class ExampleScript : MonoBehaviour {
NetworkView networkView;
void Start() {
networkView = new NetworkView ();
networkView.RPC ("PrintText", RPCMode.All, "Hello world");
}
}
C# スクリプトの例
networkView.RPC ("PrintText", RPCMode.All, "Hello world");
JS スクリプトの例
RPC() の最初の引数は実行する関数の名前で、2 つめの引数は実行ターゲット対象を指定します。この場合、サーバー接続しているクライアントすべてで実行します。(後ほど接続されるクライアント向けを待ってコールがバッファリングされることはありません、このバッファリングの詳細は以下を参照してください)
2 つ目の引数より後は、RPC 関数に送信され、ネットワーク上を経由します。この場合では“Hello World”は引数として PrintText 関数のテキスト引数として渡されます。
さらに追加の内部引数として、RPC の呼び出し元など追加の情報を保持できる NetworkMessageInfo 構造体を参照できるようになります。この情報は自動的に送信されるため、PrintText 関数は次のように宣言されます:
using UnityEngine;
using System.Collections;
public class ExampleScript : MonoBehaviour {
[RPC]
void PrintText (string text, NetworkMessageInfo info)
{
Debug.Log(text + " from " + info.sender);
}
}
C# スクリプトの例
@RPC
function PrintText (text : String, info : NetworkMessageInfo)
{
Debug.Log(text + " from " + info.sender);
}
JS スクリプトの例
この際、関数実行の記述は変更の必要がありません。
上で述べたように Network View を RPC 関数を含むスクリプトを含むゲームオブジェクトにアタッチする必要があります。もし RPC を独立させて使用する場合(すなわち、状態同期なし)、Network View の State Synchronization を Off にします。
RPC 関数の呼び出しはバッファリングできます。バッファリングされた RPC 関数の呼び出しは蓄積されたうえ、発行された順序で接続するクライアントごとに並べられます。これにより、遅れてきたプレイヤーがスタート時点から必要な情報が得られることを保証します。良くあるシナリオとしては、接続するプレイヤーがまず特定のレベルをロードするというシナリオです。このレベルの詳細をすべての接続したプレーヤーに送信することもできますが、将来的に後から接続するプレイヤーのためにバッファリングすることもできます。これにより、新しいプレイヤーがあたかもスタートの最初から存在したかのごとくそのレベル情報を受信できます。
RPC バッファから必要に応じて呼び出しを除くことができます。上の例で続けると、新しいプレイヤーが加わる前にゲームが次のレベルに進んでいる場合があり、この場合は元のバッファリングされた RPC を除いて、新しいレベルを要求するリクエストを送信することができます。