Search Unity

  1. If you have experience with import & exporting custom (.unitypackage) packages, please help complete a survey (open until May 15, 2024).
    Dismiss Notice
  2. Unity 6 Preview is now available. To find out what's new, have a look at our Unity 6 Preview blog post.
    Dismiss Notice

Bug IN-30127 Cannot call SerializationUtility.SetManagedReferenceIdForObject with Enum

Discussion in 'Editor & General Support' started by CDF, Jan 27, 2023.

  1. CDF

    CDF

    Joined:
    Sep 14, 2013
    Posts:
    1,319
    This is a very frustrating issue. For whatever reason, Unity will not allow setting the managed reference id of an Enum value. And returns an error: "The provided object cannot be assigned a managed reference ID because it cannot be serialized on a [SerializeReference] field."

    However, Unity can and does serialize an Enum correctly, and even assigns it an id internally.
    So why can't we?

    Code (CSharp):
    1. public enum SomeEnum1 {
    2.     None,
    3.     Value1,
    4.     Value2,
    5.     Value3,
    6.     Value4,
    7.     Value5,
    8.     Value6,
    9.     Value7,
    10.     Value8,
    11.     Value9,
    12. }
    13.  
    14. [CreateAssetMenu(fileName = "New MyObject", menuName = "Test/My Object")]
    15. public class MyObject : ScriptableObject {
    16.  
    17.     [SerializeReference]
    18.     public Enum enumValue;
    19.  
    20.     public void Reset() {
    21.  
    22.         enumValue = SomeEnum1.Value1;
    23.     }
    24. }
    25.  
    26. [CustomEditor(typeof(MyObject))]
    27. class MyObjectEditor : Editor {
    28.  
    29.     private SerializedProperty enumValue;
    30.  
    31.     private void OnEnable() {
    32.  
    33.         enumValue = serializedObject.FindProperty(nameof(enumValue));
    34.     }
    35.  
    36.     public override void OnInspectorGUI() {
    37.  
    38.         serializedObject.Update();
    39.         EditorGUILayout.PropertyField(enumValue, true);
    40.         EditorGUILayout.LongField("Id", enumValue.managedReferenceId);
    41.         serializedObject.ApplyModifiedProperties();
    42.  
    43.         if (GUILayout.Button("Assign Managed Reference Id using SerializationUtility")) {
    44.  
    45.             AssignManagedReferenceIds();
    46.         }
    47.     }
    48.  
    49.     private void AssignManagedReferenceIds() {
    50.  
    51.         //have to clear the data before assigning new ids
    52.  
    53.         serializedObject.Update();
    54.         enumValue.managedReferenceValue = null;
    55.         serializedObject.ApplyModifiedPropertiesWithoutUndo();
    56.  
    57.         //create new objects and assign ids
    58.  
    59.         MyObject instance = target as MyObject;
    60.         instance.Reset();
    61.  
    62.         //Error - The provided object cannot be assigned a managed reference ID because it cannot be serialized on a [SerializeReference] field
    63.         SerializationUtility.SetManagedReferenceIdForObject(target, instance.enumValue, 1);
    64.     }
    65. }
    serializedEnum.png

    So what's the story here? We're not allowed to set the id, but internally Unity can?
     
  2. spiney199

    spiney199

    Joined:
    Feb 11, 2021
    Posts:
    8,074
    I think I need to ask the question, why would you want to serialise an Enum as a reference type? If you're leveraging polymorphism for what it's good for, you have no good reason to be using it for enums when you can serialise classes instead and socket actual behaviour.

    It's probably freaking out because enums are value types, and SerializeReference isn't usable on value types.
     
  3. CDF

    CDF

    Joined:
    Sep 14, 2013
    Posts:
    1,319
    I want to serialize an enum of any enum type. I could instead serialize an int + type string, but serializing Enum is much easier

    I realize the docs say no value types, but Unity does actually serialize it correctly as a reference, it’s just I can’t control that reference Id