Serialize功能
Unity3D 中提供了非常方便的功能可以幫助用戶將 成員變量 在Inspector中顯示,並且定義Serialize關系。
簡單的說,在沒有自定義Inspector的情況下所有顯示在Inspector 中的屬性都同時具有Serialize功能。
換句話說,就是你在Inspector看到什么,保存游戲的時候,這些值就會被保存成二進制文件。
本文說說可被Serialize的變量的定義方法
1. public 變量
在沒有加入任何Attribute的前提下,public變量是默認被視為可以被Serialize的。
public int MaxExp;
2. [SerializeField] Attribute
強制unity去序列化一個私有域
這是一個內部的unity序列化功能,有時候我們需要Serialize一個private或者protected的屬性,這個時候可以使用[SerializeField]這個Attribute:
[SerializeField] protected int foobar = 0;
注意: 這樣定義出的成員變量也是會在Inspector中顯示出來。
在Unity最新的UI系統中,UI屬性上方全部添加[SerializeField] ,如下所示
[SerializeField] private Button btn1;
SerializeField參考文檔:http://game.ceeger.com/Script/Attributes/SerializeField.html
3. 單獨的class或struct
Serializable是.Net自帶的序列化
有時候我們會自定義一些單獨的class/struct, 由於這些類並沒有從 MonoBehavior 派生所以默認並不被Unity3D識別為可以Serialize的結構。自然也就不會在Inspector中顯示。我們可以通過添加 [System.Serializable]這個Attribute使Unity3D檢測並注冊這些類為可Serialize的類型。具體做法如下:
[System.Serializable] public class FooBar { public int foo = 5; public int bar = 10; }
注意:Serializable只可以對class,struct,enum,delegate進行序列化,不可以對屬性序列化
4. ScriptableObject
ScriptableObject 類型經常用於存儲一些unity3d本身不可以打包的一些object,比如字符串,一些類對象等。用這個類型的子類型,則可以用BuildPipeline打包成assetbundle包供后續使用,非常方便,具體請參考 [cb]ScriptableObject 序列化
NonSerialize的變量的定義方法
4.1. protected, private, internal 變量
默認情況下,protected, private, internal變量將不會被serialize.
4.2. [System.NonSerialized] Attribute
有時候我們需要定義一些public變量方便操作,但是又不希望這些變量保留。這個時候可以利用[System.NonSerialized]來完成這個操作:
[System.NonSerialized] public float foobar = 1.0f;
4.3. readonly, const, static 修飾符
如果變量加入了readonly, const, static等修飾符,無論他的serialize設置如何,都將不會進行serialize
4.4. Dictionary<T,K>
Unity3D可以對List<T>進行序列化顯示,但是由於他們的程序員偷懶或不夠強大,以至於我們到現在都不能serialize Dictionary<T,K>這么一個較為常用的類型。通常我們會通過Serialize一份List<T>,然后在 Awake中初始化Dictionary的方法來完成Dictionary的serialize操作。如:
[System.Serializable] public class NameToID { public string name = ""; public int ID = -1; }
public List<NameToID> nameToIDList = new List<NameToID>();
Dictionary<string,int> nameToID = new Dictionary<string,int>();
// void Awake () { foreach ( NameToID info in nameToIDList ) { nameToID[info.name] = info.ID; } nameToIDList = null; // put it null make garbage collect it (I wish) }
在Inspector中的顯示
變量在Inspector中會根據變量的大寫字母來隔開來顯示,並且會將首字母強制大寫的方式顯示。 如:
public int myFooBar = 0;
在GUI將會顯示為: My Foo Bar