指示 Unity 将字段序列化为引用。
除非字段类型派生自 [UnityEngine.Object],否则 Unity 在序列化对象时会将所有字段都序列化为值类型。
默认情况下,不支持多态字段,也无法在原生表示基于引用的拓扑,如图形。
建议从 ScriptableObject 派生字段类型,因为这样通常可以获得最佳性能。
但如果使用 ScriptableObjects 导致复杂程度无法接受,则用 [SerializeReference] 修饰字段可指示 Unity“按引用”而非“按值”序列化字段。
注意:
- 字段类型不能是用于序列化 UnityEngine.Object 的类型。
- 字段类型可以是抽象的。
- 字段类型可以是接口。
- 用 [SerializeReference] 修饰的通用列表和数组字段将属性应用于列表/数组的元素,而非列表/数组实例本身。
- UnityEngine.Object 实例之间不能共享引用的值。例如,两个 MonoBehaviours 不能共享按引用序列化的对象。请使用 ScriptableObjects 而非共享数据。
- 字段值可以是 null。
- 字段值不能是通用类型(扩大的类型)的特化表示。
- 分配给字段的动态实例/对象的类型必须是 [Serializable] 类型。
- 字段类型也支持“System.Object”、“List<System.Object>”或“System.Object[]”类型。
using System; using System.Collections.Generic; using UnityEngine;
public interface IShape {}
[Serializable] public class Cube : IShape { public Vector3 size; }
[Serializable] public class Thing { public int weight; }
[ExecuteInEditMode] public class BuildingBlocks : MonoBehaviour { [SerializeReference] public List<IShape> inventory;
[SerializeReference] public System.Object bin;
[SerializeReference] public List<System.Object> bins;
void OnEnable() { if (inventory == null) { inventory = new List<IShape>() { new Cube() {size = new Vector3(1.0f, 1.0f, 1.0f)} }; Debug.Log("Created list"); } else Debug.Log("Read list");
if (bins == null) { // This is supported, the 'bins' serialized field is declared as holding a collection type. bins = new List<System.Object>() { new Cube(), new Thing() }; }
if (bin == null) { // !! DO NOT USE !! // Although, this is syntaxically correct, it is NOT supported as a valid serialization construct because the 'bin' serialized field is declared as holding a single reference type. bin = new List<System.Object>() { new Cube() }; } } }