コンテンツにスキップ

VRChatのオーナーシップが確定するタイミング

LateJoiner(後から入ってきた人)のオブジェクトのオーナーシップの情報がどの段階で確定するか調べてみた。

検証環境

com.vrchat.worlds 3.4.0
com.vrchat.base 3.4.0

結論

OnEnableの段階で確定する。Networking.GetOwnerで取得できるオーナー情報は、LateJoinerであってもいつでも正しい情報が取得できると考えてよさそう。

検証コード

各イベント関数内でNetworking.LocalPlayerNetworking.GetOwner(gameObject)、ついでにマニュアル同期変数の値をチェックしている。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
using UdonSharp;
using UnityEngine;
using VRC.SDKBase;
using VRC.Udon;


[UdonBehaviourSyncMode(BehaviourSyncMode.Manual)]
public class OwnerShipTimingCheck : UdonSharpBehaviour
{
    [UdonSynced]
    int syncValue = 0;

    void CheckOwnerAndLocal(string functionName)
    {
        var localIndex = Utilities.IsValid(Networking.LocalPlayer) ? Networking.LocalPlayer.playerId.ToString() : "NULL";
        var ownerIndex = Utilities.IsValid(Networking.GetOwner(gameObject)) ? Networking.GetOwner(gameObject).playerId.ToString() : "NULL";
        Debug.Log($"TEST:{functionName}:[{localIndex}] Owner is [{ownerIndex}] : SyncValue = {syncValue}");
    }

    private void OnEnable()
    {

        CheckOwnerAndLocal("OnEnable");
    }

    void Start()
    {
        CheckOwnerAndLocal("Start");
    }

    public override void OnPlayerJoined(VRCPlayerApi player)
    {

        if (player.isLocal)
        {
            CheckOwnerAndLocal("OnPlayerJoined");

            if(player.playerId == 1)
            {
                syncValue = 3;
                RequestSerialization();
            }
        }

    }

    public override void OnDeserialization()
    {
        CheckOwnerAndLocal("OnDeserialization");
    }
}

出力結果

どのタイミングでもオーナープレイヤーのIDを正しく取得できている。 同期変数のみ、同期されるのはOnDeserializationより後。 OnDeserializationは基本的にOnPlayerJoinedより後に呼ばれてる?

1
2
3
4
5
6
7
8
9
[一人目がインスタンスにJoin]
TEST:OnEnable:[1] Owner is [1] : SyncValue = 0
TEST:Start:[1] Owner is [1] : SyncValue = 0
TEST:OnPlayerJoined:[1] Owner is [1] : SyncValue = 0
[二人目がインスタンスにJoin]
TEST:OnEnable:[2] Owner is [1] : SyncValue = 0
TEST:Start:[2] Owner is [1] : SyncValue = 0
TEST:OnPlayerJoined:[2] Owner is [1] : SyncValue = 0
TEST:OnDeserialization:[2] Owner is [1] : SyncValue = 3