ネットワーク

同期フィールド、カスタムイベント、型付きネットワークイベント、そして NetworkTransform コンポーネント。

更新日 2026-09-03

Udonite は内部で VRChat 自身のネットワーク機能を使います。規則は通常の Udon ビヘイビアと同じです。GameObject の同期状態を書き換えられるのはそのオーナーだけで、ネットワーク越しに呼べるのは public メソッドだけです。

同期フィールド

フィールドに [UdonSynced] を付け、ビヘイビアの同期モードを設定します。

using Udonite.Package.Runtime;
using UnityEngine;
using VRC.SDKBase;
using VRC.Udon.Common;

[UdonBehaviourSyncMode(BehaviourSyncMode.Manual)]
public class Counter : UdoniteBehaviour
{
    [UdonSynced] public int count;

    public override void Interact()
    {
        if (!Networking.IsOwner(gameObject))
            Networking.SetOwner(Networking.LocalPlayer, gameObject);

        count = count + 1;
        this.RequestSerialization();
    }

    public override void OnDeserialization(DeserializationResult result)
    {
        Debug.Log("count is now " + count);
    }
}
  • BehaviourSyncMode.Manualthis.RequestSerialization() を呼んだときに送信します。Continuous は自動で送信し、None は何も同期しません。
  • [UdonSynced(UdonSyncMode.Linear)]Smooth は、受信側で数値フィールドを補間します。
  • OnPreSerializationOnPostSerializationOnDeserialization が転送の前後に呼ばれます。

変更に反応する

[FieldChangeCallback] はプロパティ名を指定します。同期された値が届くたびに、そのプロパティの setter が実行されます。

[UdonSynced, FieldChangeCallback(nameof(Lit))]
private bool lit;

public bool Lit
{
    get => lit;
    set
    {
        lit = value;
        lamp.SetActive(value);
    }
}

プロパティの型は、フィールドの型と厳密に一致している必要があります。

カスタムイベント

public メソッドは名前を指定して他のクライアントに送れます。

this.SendCustomNetworkEvent(NetworkEventTarget.All, nameof(Ring));

public void Ring()
{
    bell.Play();
}

NetworkEventTarget.Owner はそのオブジェクトのオーナーにだけ送ります。SendCustomEventDelayedSecondsSendCustomEventDelayedFrames は、ローカルでの呼び出しを後回しにします。

型付きネットワークイベント

構造のあるペイロードを送りたいときは、SerializeDeserialize の対を持つイベントクラスを定義し、受信側のビヘイビアにハンドラを置きます。

using Udonite.Package.Runtime;
using UnityEngine;

public class ScoreEvent : NetworkEvent
{
    public int player;
    public int score;

    public void Serialize(ByteWriter writer)
    {
        writer.WriteInt32(player);
        writer.WriteInt32(score);
    }

    public void Deserialize(ByteReader reader)
    {
        player = reader.ReadInt32();
        score = reader.ReadInt32();
    }
}

public class Scoreboard : UdoniteBehaviour
{
    public void Award(int player, int score)
    {
        ScoreEvent evt = new ScoreEvent();
        evt.player = player;
        evt.score = score;
        Udonite.Network.Send(evt, this);
    }

    [NetworkEventHandler]
    public void OnScore(ScoreEvent evt)
    {
        Debug.Log("player " + evt.player + " scored " + evt.score);
    }
}

Udonite.Network.Send(evt, receiver) はイベントをシリアライズし、receiver にある、そのイベント型を引数に取る [NetworkEventHandler] メソッドへ、すべてのクライアントで届けます。必ず完全修飾で書いてください。using UnityEngine; がある状態では、裸の Network は Unity の廃止された UnityEngine.Network と衝突します。中身は同期フィールドで運ばれるため、他のクライアントに届くのは receiver の GameObject のオーナーが呼んだときだけです。

NetworkTransform

NetworkTransform は、位置・回転・スケールを補間とテレポート検出つきで同期する、そのまま使えるビヘイビアです。オブジェクトに追加してコンパイルし、動かすだけです。同じオブジェクトに VRC_Pickup があれば、持ち上げるとオーナーシップを取得し、放すと静止した姿勢を送ります。送信レート、チャンネルごとのしきい値、テレポート判定距離はインスペクタのフィールドです。

オーナーシップ

OnOwnershipRequest を override して false を返せば、移譲を拒否できます。OnOwnershipTransferred はオーナーが変わったときに全クライアントで呼ばれます。ClientSim はオーナーシップの要求を発火しないため、その確認はアップロードしたワールドで行ってください。

Something went wrong. Reload