Unity JsonUtility によるデ/シリアライズと型の確認

Unityのロゴ。

Unity のバージョン 5.3.x からあるオブジェクトに定義される public フィールドを JSON として出力するための JsonUtility クラスが追加されました。 アプリケーションの設定情報などを簡単に保存しておくために重宝します。ここでは保存できる型や仕様を簡単に確認し、実際にファイル出力したり読み込んで、シリアライズ・デシリアライズするサンプルを紹介します。

サンプルはすべて github にアップしています。SampleClass に検証対象となるフィールドをすべて定義しています。 JsonUtility で JSON にした後、ファイルに出力して再度そのファイルからデシリアライズします。

多くの資料を見ていると、5.3.x 時点と 5.4.x 時点とでシリアライズできる型(対象)が異なり、5.4 ではより多くの対象を(デ)シリアライズできるようになったようです。 したがってここで対応してないと言及している型についても、最新のバージョンでは対応している可能性があります。 詳細はコードを読むなりサンプルシーンを実行するなりして確認してください。

JsonUtility を試験するためにインスペクタに大量のフィールドを表示した様子。

シリアライズできる型・できない型

シリアライズできる型は概ねインスペクタに表示することができる型です。 したがって、[Serializalbe]属性を設定した構造体やクラスもシリアライズすることができます。

また原則として public フィールドしかシリアライズされませんが、 private フィールドであっても、[SerializeField] 属性を設定すればシリアライズされます。

比較的特殊な型としては次のものがあげられます。

  • クラス(Serializable)
  • 構造体(Serializable)
  • List<T>
  • T[](Array / 配列)
  • 列挙型

現在のところシリアライズできない型などは次の通りです。

  • object
  • Dictionary
  • T[][] (Jagged Array / 多次元配列)
  • static なフィールド
  • プロパティ

Unity 固有の型について

また Unity では Vector2 や Matrix, Quaternion などの型がよく扱われますが、これらもすべてシリアライズすることができます。 ただし、唯一 Transform だけは特殊な扱いになっています。

Transform は TransformID、つまり、シーン上に存在するどの Transform かを示す値が保存されます。 したがって、Transform の持つ、Position, Rotation, Scale の値がそのまま JSON にシリアライズされるわけではありません。

Dictionary などの対応について

Dictionary などについては、ISerializationCallbackReceiver を実装することで解決することができるようです。 次の URL などが参考になります。結構手間ですね。

Dictionary などにも対応した JSON ライブラリを使うのも手だと思います。ただし JsonUtility はパフォーマンス面などで優位にあることが公式で言及されています。

パフォーマンスについて

オフィシャルにパフォーマンスが優れているとされていますが、実際に運用されているシステムで、検証されている方がいらっしゃいました。 メモリ効率なども良いみたいですね。