ネットコードで共有ARシーンを設定する方法
Shared ARは、ARとネットワーク機能のセットで、マルチプレイヤーAR体験を作ることができる。 このハウツーでは、GameObjects用のUnity Netcodeを使用して、ネットワークマルチプレイヤーのセットアップ、リアルワールドトラッキングの有効化、Lightshipネットワークサーバーへの接続を学びます。

前提条件
- Lightship ARを有効にしたUnityプロジェクトが必要です(../../setup.md)。
 - Shared ARプラグインをインストール](../../setup.md#setting-up-lightship-ardk)する必要があります。
 - ARSessionとXROrigin](../../setup.md#setting-up-a-basic-ar-scene)を持つARシーンが必要です。
 - UnityドキュメントのGet started with NGOから、Netcode for Gameobjectsの概念と使い方を理解する。
 

シーンにコンポーネントを追加する
Shared ARを使用するには、これらのコンポーネントをUnityシーンに追加する必要があります:
- 
シーンのルートにNetwork Managerオブジェクトを追加してください。
- HierarchyでARシーンを右クリックし、Create Emptyを選択します。 新しいGameObjectにNetworkManager**という名前を付ける。
 
 - 
NetworkManager` GameObjectにNetworkManagerコンポーネントを追加する。
- 階層**で、NetworkManagerを選択する。
 - Inspector**ウィンドウで、Add Componentをクリックします。
 - 検索ボックスに「Network Manager」と入力し、選択して追加する。
 - ネットワーク・トランスポート**で、トランスポートを選択...をクリックし、LightshipNetcodeTransportを選択します。 これで自動的にLightship Netcode Transportコンポーネントが追加されます。
 
 - 
XROrigin** に SharedSpaceManager コンポーネントを追加します:
- 
ARシーンの階層で、
XR Originを選択します。 - 
Inspector**ウィンドウで、Add Componentをクリックします。
 - 
検索ボックスに "Shared Space Manager "と入力して選択し、
XR Originに追加します。 - 
Shared Space ManagerのColocalization TypeをMock Colocalizationに設定する。 VPS Colocalization](./use_vps_colocalization_with_netcode.md)またはImage Tracking Colocalizationを使用する場合は、必ず対応するColocalization Typeに変更してください。
 
 - 
 
SharedSpaceManagerでNetcodeセッションを開始する
SharedSpaceManager`を使って、次にシーンとコードをセットアップし、ユーザーが互いに接続してネットワーク・セッションを開始できるようにする。
SharedARのUIとマネージャーを設定する:
- 
Hierarchy**で、ARシーンの下で右クリックし、UIメニューを開き、Button - TextMeshProを選択してボタンを追加します。 この作業を繰り返し、別のボタンとテキスト・フィールドを追加する。 ボタンはホストとクライアントを参加させるためのもので、テキストフィールドは接続ステータスを出力するためのものです。 ボタンの名前を
JoinAsHostとJoinAsClientとし、テキストフィールドの名前をLocalizationStatusTextとする。 - 
Hierarchy**で、ARシーンのルートを右クリックし、Create Emptyを選択します。 新しいオブジェクトの名前を
NetworkDemoとする。 - 
プロジェクト(Project)ウィンドウの**資産(Assets)フォルダで右クリックし、作成(Create)メニューを開いてC#スクリプト(C# Script)を選択します。 新しいスクリプトに
NetworkDemoManager.csという名前を付ける。- NetworkDemoManager.cs
を開き、UI要素とSharedSpaceManager`を初期化するために、そのコードを以下のスニペットで置き換える: 
using Niantic.Lightship.SharedAR.Colocalization;
using Unity.Netcode;
using UnityEngine;
using UnityEngine.UI;
public class NetworkDemoManager : MonoBehaviour
{
[SerializeField]
private Text _statusText;
[SerializeField]
private Button _joinAsHostButton;
[SerializeField]
private Button _joinAsClientButton;
[SerializeField]
private SharedSpaceManager _sharedSpaceManager;
}
void Start()
{
// We will fill this in later!
} - NetworkDemoManager.cs
 - 
NetworkDemoManager.cs
のフィールドをNetworkDemo` に接続する:- AR Scene の Hierarchy で、NetworkDemo コンポーネントを選択します。
 - Inspector**ウィンドウで、Add Componentをクリックします。
 - 検索ボックスに「Network Demo Manager」と入力し、選択して追加する。
 - テキストフィールド、ボタン、そして**SharedSpaceManager
を含む**XR Origin** を、**Hierarchy**から**Network Demo Manager**コンポーネントの対応するフィールドにドラッグアンドドロップします。 この時点で、NetworkDemo`はこうなっているはずだ: 
 
部屋の作成とイベントの処理
次に、スクリプトにコードを追加して、マルチプレイヤールームを作成し、ユーザー接続などの共有ARイベントを処理する。 Network Demo Managerをマルチプレイに対応させる:
- 
NetworkDemoManager.cs` にコードスニペットを追加する:
- ISharedSpaceTrackingOptions.CreateMockTrackingOptions()`を呼び出して、部屋のトラッキングオプションを作成します。
 - ISharedSpaceRoomOptions.CreateLightshipRoomOptions()`を使用してルームオプションを作成し、マルチプレイヤールームをインスタンス化します。
 - SharedSpaceManager
にsharedSpaceManagerStateChangedイベントのハンドラを追加する。 次のコード・スニペットをコピーして、この機能をNetworkDemoManager.cs` に追加してください: 
protected void Start()
{
// Set room to join
var mockTrackingArgs = ISharedSpaceTrackingOptions.CreateMockTrackingOptions();
var roomArgs = ISharedSpaceRoomOptions.CreateLightshipRoomOptions(
"ExampleRoom", // use fixed room name
32, // set capacity to max
"vps colocalization demo (mock mode)" // description
);
_sharedSpaceManager.StartSharedSpace(mockTrackingArgs, roomArgs);
} 
次に、いくつかの重要なイベントについて説明し、Network Demo Managerスクリプトにイベント処理コードを追加します:
- トラッキングステータスが変更されると、
SharedSpaceManager.sharedSpaceManagerStateChangedが呼び出される。 このイベントを見て、良いトラッキング状態になるのを待ってから次に進むことで、ユーザーはエクスペリエンス開始前にトラッキングの動作に集中することができ、ビジュアルコンテンツが不適切に動く可能性を減らすことができます。 模擬コロカライゼーション・モードでは、このイベントは即座に起動される。 - 接続が確立されると、
NetworkManager.OnClientConnectedCallbackが呼び出される。 ここでは、シングルトン版のコールバック、NetworkManager.Singleton.OnClientConnectedCallbackを設定し、ホストがプレーヤーの接続をキャッチするようにしています。 (プレイヤーがクライアントの場合、このイベントはホストが参加した ときに発生します)。 この例では、新しい接続を通知するテキストも追加している。 - ホストとして Netcode セッションを開始するには、
NetworkManager.Singleton.StartHostを呼び出します。 代わりにクライアントとして起動するには、NetworkManager.Singleton.StartClientを呼び出します。 この例では、これらのイベントをそれぞれのボタンに追加し、ユーザーが必要に応じてホストまたはクライアントとして参加できるようにします。 
NetworkManagerスクリプトを表示するにはクリックしてください。
  ```cs
  protected void Start()
  {
     // UI event listeners
     _joinAsHostButton.onClick.AddListener(OnJoinAsHostClicked);
     _joinAsClientButton.onClick.AddListener(OnJoinAsClientClicked);
     // Netcode connection event callback
     NetworkManager.Singleton.OnClientConnectedCallback += OnClientConnectedCallback;
     // Set SharedSpaceManager and start it
     _sharedSpaceManager.sharedSpaceManagerStateChanged += OnColocalizationTrackingStateChanged;
     // Set room to join
     var mockTrackingArgs = ISharedSpaceTrackingOptions.CreateMockTrackingOptions();
     var roomArgs = ISharedSpaceRoomOptions.CreateLightshipRoomOptions(
           "ExampleRoom", // use fixed room name
           32, // set capacity to max
           "vps colocalization demo (mock mode)" // description
        );
     _sharedSpaceManager.StartSharedSpace(mockTrackingArgs, roomArgs);
  }
  private void OnColocalizationTrackingStateChanged(
     SharedSpaceManager.SharedSpaceManagerStateChangeEventArgs args)
  {
     if (args.Tracking)
     {
        _joinAsHostButton.gameObject.SetActive(true);
        _joinAsClientButton.gameObject.SetActive(true);
     }
  }
  private void OnJoinAsHostClicked()
  {
     NetworkManager.Singleton.StartHost();
     HideButtons();
  }
  private void OnJoinAsClientClicked()
  {
     NetworkManager.Singleton.StartClient();
     HideButtons();
  }
  private void HideButtons()
  {
     _joinAsHostButton.gameObject.SetActive(false);
     _joinAsClientButton.gameObject.SetActive(false);
  }
  private void OnClientConnectedCallback(ulong clientId)
  {
     Debug.Log($"Client connected: {clientId}");
  }
  ```
1人のユーザーがホストで、残りがクライアントであることを確認してください。
ファイナル・ネットワーク・デモ・マネージャー・スクリプト
この時点で、NetworkDemoManager.csは次のようになっているはずだ:
クリックすると、完成したNetwork Demo Managerのコードが表示されます。
using Niantic.Lightship.SharedAR.Colocalization;
using Unity.Netcode;
using UnityEngine;
using UnityEngine.UI;
public class NetworkDemoManager : MonoBehaviour
{
   [SerializeField]
   private Text _statusText;
   [SerializeField]
   private Button _joinAsHostButton;
   [SerializeField]
   private Button _joinAsClientButton;
   [SerializeField]
   private SharedSpaceManager _sharedSpaceManager;
   protected void Start()
   {
      // UI event listeners
      _joinAsHostButton.onClick.AddListener(OnJoinAsHostClicked);
      _joinAsClientButton.onClick.AddListener(OnJoinAsClientClicked);
      // Netcode connection event callback
      NetworkManager.Singleton.OnClientConnectedCallback += OnClientConnectedCallback;
      // Set SharedSpaceManager and start it
      _sharedSpaceManager.sharedSpaceManagerStateChanged += OnColocalizationTrackingStateChanged;
      // Set room to join
      var mockTrackingArgs = ISharedSpaceTrackingOptions.CreateMockTrackingOptions();
      var roomArgs = ISharedSpaceRoomOptions.CreateLightshipRoomOptions(
            "ExampleRoom", // use fixed room name
            32, // set capacity to max
            "shared ar demo (mock mode)" // description
      );
      _sharedSpaceManager.StartSharedSpace(mockTrackingArgs, roomArgs);
   }
   private void OnColocalizationTrackingStateChanged(
      SharedSpaceManager.SharedSpaceManagerStateChangeEventArgs args)
   {
      // Show Join UI
      if (args.Tracking)
      {
            _joinAsHostButton.gameObject.SetActive(true);
            _joinAsClientButton.gameObject.SetActive(true);
      }
   }
   private void OnJoinAsHostClicked()
   {
      NetworkManager.Singleton.StartHost();
      HideButtons();
   }
   private void OnJoinAsClientClicked()
   {
      NetworkManager.Singleton.StartClient();
      HideButtons();
   }
   private void HideButtons()
   {
      _joinAsHostButton.gameObject.SetActive(false);
      _joinAsClientButton.gameObject.SetActive(false);
   }
   private void OnClientConnectedCallback(ulong clientId)
   {
      _statusText.text = $"Connected: {clientId}";
   }
}

次のステップ
VPS Colocalization with Netcodeを使用してAR Multiplayerを開始する方法については、How to use VPS Colocalization with Netcodeを参照してください。