【VRChat/UdonSharp】FixedUpdateの罠
予防線
2023年6月時点での話です。今後仕様が変わる可能性はありますし(あってくれ)、私の知識に間違いがある可能性もあります。
FixedUpdateを使いたい
事前知識
必要かは分かりませんが、一応説明。
VRChatのU#(というかUnity)において、常時動き続けるイベントにUpdateとLateUpdateとFixedUpdateがあります。(他にもあるかも)
Updateは毎フレーム呼ばれます。LateUpdateはUpdateの処理が終わった後に呼び出されます。
そしてFixedUpdateは一定間隔で呼ばれます。
UnityにおけるFixedUpdate
デフォルトでは50FPS、0.02秒間隔、つまり1秒に50回呼ばれます。
これはProject Settingから変更することもできて、割と融通の効く良い子です。
U#におけるFixedUpdate
人によって動作が違う
U#のFixedUpdateはプレイヤーのモニターのリフレッシュレートで呼ばれます。
なんのこっちゃ?となるかもしれませんので説明。
モニター毎に何FPSまで表示できるかは違いがあります。それを表したのがリフレッシュレートです。
一般的なモニターなら60Hz(つまり60FPS)、ゲーミングモニターなら144Hz(144FPS)くらいが普通ですかね。
つまり、プレイヤーによってFixedUpdateが呼び出される間隔が違います。
60Hzのモニターのプレイヤーが見ているワールドのFixedUpdateは60FPSで動きます。
同じワールドにいる144HzのモニターのプレイヤーはFixedUpdateが144FPSで動いています。
これはVRHMDでも同じです。そのHMDのリフレッシュレートで動きます。
変更ができない
この間隔を変更する手段はありません。なんで?
そしてその事は公式のどこにも書いてはいない
書いてません。
挙動が個々人のモニター依存なため、デバッグ時点では気付かない可能性もあります。
結論
残念ながらUpdateの方が安全です。
それでも使いたい場合、世の中には30Hzのモニターが存在する事を覚えておくといいかもしれません。ゲーミングモニターだと今は360Hzとかあるらしいですよ。
おまけ
あとUpdateとかFixedUpdateはStartの前に呼び出される事があります。
(呼び出されない事もある)
private int[] _numArray;
void Start()
{
_numArray = new int[5];
}
void FixedUpdate()
{
for(int i; i < _numArray.Length; i++)
{
//なんか処理
}
}
こういうのはたまにエラーが出ます。なんで?
Discussion