ネットワークオブジェクト
概要
NetworkObject
コンポーネントは GameObject
にネットワーク ID を割り当てて、ネットワーク上で共有できるようにします。全てのプレイヤーに表示され、シーンの一部となる GameObject
は、 NetworkObject
スクリプトを持つ必要があります。
Fusion では、NetworkObject
にカスタムのネットワーク動作を作成するためのクラスが2つ用意されています。
- シミュレーション関連のビヘイビアを作成する
SimulationBehaviour
と、 NetworkBehaviour
は[Networked]
状態を維持、または追跡する動作です
NetworkObject
GameObject
のルートノードにある NetworkObject
スクリプト一つで、階層全体をコントロールすることができます。実行時に NetworkObject
は、その階層にある全ての SimulationBehaviour
と NetworkBehaviour
を探します。
必要であれば、NetworkObject
をネストすることができます。この場合、NetworkObject
はネストした子オブジェクトを検索せず、子オブジェクトの NetworkObject
にその下の SimulationBehaviour
と NetworkBehaviour
をすべて追跡させることができます。典型的な使用例としては、運転手がシャシーの方向(移動)をコントロールし、射撃者がタレット(射撃)をコントロールする2人乗り戦車です。
プレハブ / オブジェクトテーブル
Fusion で Prefab
パラメータが意味を持つようにするには(そして全てのクライアントが正確にどのプレハブであるかに同意するようにするには)、プレハブ自体が Fusion に登録されている必要があります。通常であれば、Fusionツールセットが自動的にプレハブを検出し登録しますが、手動で検出することも可能です。その場合は、NetworkProjectConfig
を選択し、Unity InspectorでRebuild Object Table
を押します。
インスタンス化 / スポーン
NetworkObject
プレハブのインスタンス化は、2つのステップを必要とします。
- 編集時: クライアントが
NetworkProjectConfig
アセットで、NetworkObject
プレハブの ID を一致させる必要があることを確認します。これは、NetworkProjectConfig
アセットでRebuild Object Table
を実行することで行われます。 - 実行時:
NetworkRunner
のSpawn()
を、NetworkObject
プレハブをパラメータとして呼び出します。
__ 重要:__ Unity の一般的な Instantiate()
メソッドを呼び出すと、壊れたローカルインスタンスが作成されます!
破壊 / デスポーン
NetworkObject
を破棄するには、 Runner.Despawn()
を呼び出し、パラメータとしてオブジェクトを渡してください。これはオブジェクトだけでなく、ネストした全てのオブジェクトを破壊します。トップオブジェクトだけをデスポーンするには、ネストしたオブジェクトをまず手動でデペアレンティングする必要があります。
NetworkObject の検索
ネットワークオブジェクトのインスタンスを参照する NetworkId
を渡すことで、 NetworkRunner.TryFindObject()
を使って NetworkObject
を見つけることができます。
NetworkId
と NetworkObject
は [Networked]
属性でネットワーク化できますが、NetworkObject
をネットワーク化すると Game State に NetworkId
を追加するだけです(実際の NetworkObject
のデータはバッファにコピーされず、その参照のみが行われます)。
Networked] NetworkObject
にアクセスするときは、あらかじめ NetworkRunner.TryFindObject()
が実行されますので、ID をネットワークして手動で行うか、オブジェクトそのものをネットワークするかは開発者の選択となります。
State Authority
State Authorityは、[Networked]
プロパティの正しい値を変更し決定する権利を持つ人を示します。
概念自体はFusionの全てのトポロジーで同じですが、機能的な違いがあります。
ServerModeとHostMode
ServerModeとHostModeでは、サーバ/ホスト上のシミュレーションは単一状態権限です。そのため、Object.HasStateAuthority
を使ったif文で、そこでしか実行されないはずのコードパスをカプセル化することが可能です。Object.HasStateAuthority
は、サーバー/ホスト上でしか true を返しません。
Server/Clientモードでは、この値は常に PlayerRef.None
となります。Server/Hostピアは常にState Authorityとして機能するからです。
SharedMode
SharedMode
では、プレイヤー間で状態権限が_共有_されます。各プレイヤーはシミュレーション内のある数のオブジェクトに対して状態権限を持つことができます。したがって、Object.HasStateAuthority
は、その権限を持つプレイヤーに対してtrueを返します。Photon Shared ServerはNetworkObjects
のState Authorityを_管理_しますが、それらのオブジェクトに対するState Authorityは持ちません。
State Authorityは、NetworkObject
の状態(Networked Properties)の最終的な権限がどのPlayerRef
のピアにあるかを示し、そのNetworked Propertyの値はTick Snapshotsとして他のクライアントへレプリケートされます。
注意: StateAuthority
プロパティは Shared Mode にのみ適用されます。
NetworkObject
の State Authority は SharedMode
で変更することができますが、与えられたオブジェクトに対してそれを持つプレイヤーは常に一人だけです。複数のプレイヤーが同じオブジェクトの状態権限を持つことはできません!
DestroyWhenStateAuthorityLeaves
: このNetworkObject
がStateAuthority
を持つプレイヤーによってゲームから離れた時に自動的にデスポーンされるかどうかを指定します。AllowStateAuthorityOverride
: 他のプレイヤーが既に状態権限を持っている場合に、そのプレイヤーが状態権限を取得できるかどうかを示します。このプロパティはスポーン後に変更することができないため、スポーン前に設定する必要があります。ほとんどの使用例では、プレハブやシーンオブジェクトのAllowStateAuthorityOverride
を有効のままにしておいてください。ReleaseStateAuthority()
: 現在の状態権限者はオブジェクトの制御を解放します。RequestStateAuthority()
: クライアントから呼び出され、PlayerRef
をNetworkObject
のState Authorityとして割り当てることができます。Photon Shared Serverは以下の場合にのみリクエストを許可します。- オブジェクトは
AllowStateAuthorityOverride
を有効にしている。 - Object に現在の State Authority がない。これは、State Authorityがゲームセッションから離脱したか、または以前にオブジェクトに対して
ReleaseStateAuthority()
を呼び出してコントロールを放棄したためである可能性があります。
- オブジェクトは
StateAuthorityChanged()
: オブジェクトに対する状態の権限が変更されたときにIStateAuthorityChanged
インターフェースの実装から呼び出されるコールバック。
入力権限(InputAuthority)
InputAuthority
プロパティは、この NetworkObject
の FixedUpdateNetwork
において GetInput()
が呼ばれたときに、どの PlayerRef
の入力データ (INetworkInput
) が返されるかを表します。プレイヤー入力は、Input Authority を持つクライアントと State Authority のみが利用できます。その他のクライアント(プロキシ)は、GetInput()
が呼び出されるとfalse
を返します。
InputAuthorityとFusionの INetworkInput
処理は、主に ServerMode
と HostMode
のために用意されています。しかし、SharedMode
では、ユーザーの入力はすぐにState Authorityによって消費されるので、INetworkStruct
入力システムは必須ではありません。将来的に ServerMode
や HostMode
に切り替えたときに役立つように、SharedMode
では Fusion input system を使用することが望ましいかもしれませんし、後々のリファクタリングを避けることもできます。
HasInputAuthority
:Runner.LocalPlayer == Object.InputAuthority
の場合、true
を返します。スクリプトで、NetworkRunner.LocalPlayer
がNetworkObject
のState Authorityを持っているかどうかをテストするために使用します。AssignInputAuthority()
: このメソッドに渡されたPlayerRef
にState Authorityを割り当てます。これはオブジェクトのState Authorityによってのみ変更することができます。RemoveInputAuthority()
: State AuthorityをPlayerRef.None
に設定することにより、NetworkObject
からState Authorityを削除します。これは、オブジェクトのState Authorityによってのみ変更することができます。