大致說明
Unity5引入了一套新的Json工具——JsonUtility。
總的來說就是不好用。有大量Json需求的朋友,建議出門左轉,使用其他Json庫
原本Json相對簡單,但是這套工具使用的是Unity Serializer。和我們日常使用的Json序列化有點差異。支持序列化MonoBehaviour的子類,ScriptableObject的子類以及包含[Serializable]標籤的類和結構。
這套Api主要優勢是Unity內置,在很多簡單的場景,可以方便我們開發。
基本用法
不做介紹,點擊查看官方文檔
默認爲utf-8
格式,不支持utf-8帶bom
。
如果序列化的時候遇到莫名其妙的JSON parse error: Invalid value
,可以先檢查一下是否使用了帶bom的格式。
序列化ScriptableObject和MonoBehavior
public class JsonTest : MonoBehaviour
{
/// <summary>
/// 序列化字段
/// </summary>
public int Value;
void Start()
{
// 賦值Value爲2
Value = 1;
// {"Value":1}
var json = JsonUtility.ToJson(this);
// 賦值Value爲2
Value = 2;
// 數據被重新寫入,Value賦值爲1
JsonUtility.FromJsonOverwrite(json, this);
// ArgumentException: Cannot deserialize JSON to new instances of type 'JsonTest.'
// 不支持直接反序列化生成一個MonoBehavior的子類
var fromJson = JsonUtility.FromJson<JsonTest>(json);
}
}
序列化List和Dictionary和Array
如果要支持List和Array,建議寫一個包裝類,將其包含再裏邊。並且泛型中加入[Serializable]標籤
如果要支持Dictionary,建議改寫成List。
// 沒有包含[Serializable]的類,不可被包含在序列化類內
public class Item1
{
public string Str;
}
// 包含標籤可以正常序列化
[Serializable]
public class Item2
{
public string Str;
}
public class ListCollection
{
// 可正常序列化
public List<int> Item0;
// 沒有標籤不可正常序列化
public List<Item1> Item1;
// 有標籤可以正常序列化
public List<Item2> Item2;
}
public void Run()
{
var collection = new ListCollection()
{
Item0 = new List<int>() { 0, 1, 2, 3, 4 },
Item1 = new List<Item1>() { new Item1() { Str = "1" }, new Item1() { Str = "2" } },
Item2 = new List<Item2>() { new Item2() { Str = "1" }, new Item2() { Str = "2" } }
};
// {"Item0":[0,1,2,3,4],"Item2":[{"Str":"1"},{"Str":"2"}]}
Debug.Log(JsonUtility.ToJson(collection));
// {}
Debug.Log(JsonUtility.ToJson(collection.Item0));
// {}
Debug.Log(JsonUtility.ToJson(collection.Item1));
// {}
Debug.Log(JsonUtility.ToJson(collection.Item2));
// ArgumentException: JSON must represent an object type.
var fromJson = JsonUtility.FromJson<List<int>>("[0,1,2,3,4]");
Debug.Log(fromJson.Count);
}
這裏提供一個歪果仁寫的快速包裝方法。需要的朋友可以考慮使用。
// 出處
// https://forum.unity3d.com/threads/how-to-load-an-array-with-jsonutility.375735/#post-2585129
public class JsonHelper
{
public static T[] getJsonArray<T>(string json)
{
string newJson = "{ \"array\": " + json + "}";
Wrapper<T> wrapper = JsonUtility.FromJson<Wrapper<T>> (newJson);
return wrapper.array;
}
[Serializable]
private class Wrapper<T>
{
public T[] array;
}
}