Unity製ゲームで解像度設定によって速度が変わる
と
の駄菓子兄貴リスペクトのゲーム(Unity製)を見ていて
両者に共通する解像度設定によって速度が変わるという事象
について解析してみようと思った。
そんな事しなくていいから(良心)
事象の確認
まずは事象を観察すると以下の2点が挙げられる。
- グラフィックボードの性能をあげると高速ディフェンス
- グラフィクス設定をFastestにすると高速移動
したがって「フレームレートが上がるとそれに伴い加速度が増える」というのが見えてくる。
Unityのフレーム単位での処理について
Unityでは更新処理に使われる関数が複数存在するが、主に使われるのはUpdate関数かFixedUpdate関数だろう 関数の違いについて簡単に説明する。
Update
フレーム単位ごとに呼び出される。フレームレートが90なら1秒間に90回呼び出される。 主に入力系やカメラの移動などの記述をする。
FixedUpdate
独立したタイマーから呼び出される。デフォルト設定だと0.02秒に1回呼び出される。 この関数の直後に物理演算を実行するので、物理演算(Rigidbody)に関するものはこちらに記述する。
おそらくFixedUpdateでなくUpdateでオブジェクトに力をかけて加速させている。
検証
黄色い板に乗っている間だけ加速するようなゲームを作った
基底クラスBaseAccelerator
using UnityEngine; public abstract class BaseAccelerator : MonoBehaviour { public float power = 50f; public bool isEnter = false; protected Rigidbody playerRig; public int addCount = 0; void OnCollisionEnter(Collision collision) { var obj = collision.gameObject; if (obj.CompareTag ("Player")) { playerRig = obj.GetComponent<Rigidbody> (); } isEnter = true; } void OnCollisionExit(Collision collision) { isEnter = false; } }
BaseAcceleratorを継承し、FixedUpdateで加速処理をするFUpdAccelerator
using UnityEngine; public class FUpdAccelerator : BaseAccelerator { void FixedUpdate(){ if (isEnter) { playerRig.AddForce (Vector3.right * power); addCount++; } } }
BaseAcceleratorを継承し、Updateで加速処理をするUpdAccelerator
using UnityEngine; public class UpdAccelerator : BaseAccelerator { void Update(){ if (isEnter) { playerRig.AddForce (Vector3.right * power); addCount++; } } }
結果
FixedUpdateは全ての画面解像度とQuality設定で同一の地点で止まった
一方Updateは画面解像度が下がるほど、Quality設定を下げるほど制動距離は伸びた。 640 x 480 Quality:VeryLow
1366 x 768 Quality:Ultra
結論
物理演算をさせるときはUpdateではなくFixedUpdateを使おう