SerializedProperty and Reflection

Hi!
First, I’m sorry for my poor English.

I’m developing the Android 3D app with unity using C# scripts.
For version updating system of our product with asset bundle, I am making a module that own serialize objects in run-time.(If Unity supports scripts in assetbundle, I should be not do that.)
That module works as following.

  • In editor mode, it serialize all serializable fields of all MonoBehaivours to own data structure, using SerializedProperty.
  • In run time, it deserialize all fields to new instatiated MonoBehaviour with C# reflection.

The issue is in 2nd step.
I cannot find FieldInfo of some fields obtained by SerializedProperty (specially GUIStyle).
So I made a temp code list all fields of GUIStyle object using both SerializedProperty and reflection.

That code is like this.

	[MenuItem("Test/Test SerializedProperty")]
	static void TestSerializedProperty()
	{
		if (Selection.activeGameObject == null)
			return;

		MonoBehaviour mb = Selection.activeGameObject.GetComponent<MonoBehaviour>();

		// using SerializedProperty.
		SerializedObject so = new SerializedObject(mb);
		SerializedProperty sp = so.GetIterator();

		System.Text.StringBuilder sb = new System.Text.StringBuilder();

		while (sp.NextVisible(true))
		{
			for (int i = 0; i < sp.depth; i++)
				sb.Append("  ");

			sb.Append("Filed Name: ");
			sb.Append(sp.name);
			sb.Append(", Display Name: ");
			sb.Append(sp.displayName);
			sb.Append(", Type: ");
			sb.Append(sp.type);
			sb.AppendLine();
		}

		Debug.Log(sb.ToString());

		// using reflection
		sb = new System.Text.StringBuilder();

		FieldInfo[] fis = typeof(GUIStyle).GetFields(BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance);
		foreach (FieldInfo fi in fis)
		{
			sb.Append("Filed Name: ");
			sb.Append(fi.Name);
			sb.Append(", Type: ");
			sb.Append(fi.FieldType.ToString());
			sb.AppendLine();
		}

		Debug.Log(sb.ToString());
	}

And using this code I examined my MonoBehaviour script have one public field guiStyle type of GUIStyle.
The results are like following.

Filed Name: m_Script, Display Name: Script, Type: PPtr<MonoScript>
Filed Name: guiStyle, Display Name: Gui Style, Type: GUIStyle
  **Filed Name: m_Name, Display Name: Name, Type: string**
  Filed Name: m_Normal, Display Name: Normal, Type: GUIStyleState
    Filed Name: m_Background, Display Name: Background, Type: PPtr<Texture2D>
    Filed Name: m_TextColor, Display Name: Text Color, Type: ColorRGBA
  Filed Name: m_Hover, Display Name: Hover, Type: GUIStyleState
    Filed Name: m_Background, Display Name: Background, Type: PPtr<Texture2D>
    Filed Name: m_TextColor, Display Name: Text Color, Type: ColorRGBA
  Filed Name: m_Active, Display Name: Active, Type: GUIStyleState
    Filed Name: m_Background, Display Name: Background, Type: PPtr<Texture2D>
    Filed Name: m_TextColor, Display Name: Text Color, Type: ColorRGBA
  Filed Name: m_Focused, Display Name: Focused, Type: GUIStyleState
    Filed Name: m_Background, Display Name: Background, Type: PPtr<Texture2D>
    Filed Name: m_TextColor, Display Name: Text Color, Type: ColorRGBA
  Filed Name: m_OnNormal, Display Name: On Normal, Type: GUIStyleState
    Filed Name: m_Background, Display Name: Background, Type: PPtr<Texture2D>
    Filed Name: m_TextColor, Display Name: Text Color, Type: ColorRGBA
  Filed Name: m_OnHover, Display Name: On Hover, Type: GUIStyleState
    Filed Name: m_Background, Display Name: Background, Type: PPtr<Texture2D>
    Filed Name: m_TextColor, Display Name: Text Color, Type: ColorRGBA
  Filed Name: m_OnActive, Display Name: On Active, Type: GUIStyleState
    Filed Name: m_Background, Display Name: Background, Type: PPtr<Texture2D>
    Filed Name: m_TextColor, Display Name: Text Color, Type: ColorRGBA
  Filed Name: m_OnFocused, Display Name: On Focused, Type: GUIStyleState
    Filed Name: m_Background, Display Name: Background, Type: PPtr<Texture2D>
    Filed Name: m_TextColor, Display Name: Text Color, Type: ColorRGBA
  Filed Name: m_Border, Display Name: Border, Type: RectOffset
    Filed Name: m_Left, Display Name: Left, Type: int
    Filed Name: m_Right, Display Name: Right, Type: int
    Filed Name: m_Top, Display Name: Top, Type: int
    Filed Name: m_Bottom, Display Name: Bottom, Type: int
  Filed Name: m_Margin, Display Name: Margin, Type: RectOffset
    Filed Name: m_Left, Display Name: Left, Type: int
    Filed Name: m_Right, Display Name: Right, Type: int
    Filed Name: m_Top, Display Name: Top, Type: int
    Filed Name: m_Bottom, Display Name: Bottom, Type: int
  Filed Name: m_Padding, Display Name: Padding, Type: RectOffset
    Filed Name: m_Left, Display Name: Left, Type: int
    Filed Name: m_Right, Display Name: Right, Type: int
    Filed Name: m_Top, Display Name: Top, Type: int
    Filed Name: m_Bottom, Display Name: Bottom, Type: int
  Filed Name: m_Overflow, Display Name: Overflow, Type: RectOffset
    Filed Name: m_Left, Display Name: Left, Type: int
    Filed Name: m_Right, Display Name: Right, Type: int
    Filed Name: m_Top, Display Name: Top, Type: int
    Filed Name: m_Bottom, Display Name: Bottom, Type: int
  Filed Name: m_Font, Display Name: Font, Type: PPtr<Font>
  Filed Name: m_FontSize, Display Name: Font Size, Type: int
  Filed Name: m_FontStyle, Display Name: Font Style, Type: int
  Filed Name: m_Alignment, Display Name: Alignment, Type: int
  Filed Name: m_WordWrap, Display Name: Word Wrap, Type: bool
  Filed Name: m_RichText, Display Name: Rich Text, Type: bool
  **Filed Name: m_TextClipping, Display Name: Text Clipping, Type: int**
  Filed Name: m_ImagePosition, Display Name: Image Position, Type: int
  Filed Name: m_ContentOffset, Display Name: Content Offset, Type: Vector2f
    Filed Name: x, Display Name: X, Type: float
    Filed Name: y, Display Name: Y, Type: float
  Filed Name: m_FixedWidth, Display Name: Fixed Width, Type: float
  Filed Name: m_FixedHeight, Display Name: Fixed Height, Type: float
  Filed Name: m_StretchWidth, Display Name: Stretch Width, Type: bool
  Filed Name: m_StretchHeight, Display Name: Stretch Height, Type: bool

Next is using reflection.(only for GUIStyle)

Filed Name: m_Ptr, Type: System.IntPtr
Filed Name: m_Normal, Type: UnityEngine.GUIStyleState
Filed Name: m_Hover, Type: UnityEngine.GUIStyleState
Filed Name: m_Active, Type: UnityEngine.GUIStyleState
Filed Name: m_Focused, Type: UnityEngine.GUIStyleState
Filed Name: m_OnNormal, Type: UnityEngine.GUIStyleState
Filed Name: m_OnHover, Type: UnityEngine.GUIStyleState
Filed Name: m_OnActive, Type: UnityEngine.GUIStyleState
Filed Name: m_OnFocused, Type: UnityEngine.GUIStyleState
Filed Name: m_Border, Type: UnityEngine.RectOffset
Filed Name: m_Padding, Type: UnityEngine.RectOffset
Filed Name: m_Margin, Type: UnityEngine.RectOffset
Filed Name: m_Overflow, Type: UnityEngine.RectOffset
Filed Name: m_FontInternal, Type: UnityEngine.Font

In here I bold two fields m_Name and m_TextClipping.
Those two fields are obtained by SerializedProperty but cannot be found with reflection.

How can I get those field infos using reflection?
Because of SerializedProperty is Editor class, so I cannot use it on deserialize.

Anyone help me advise, please.
Thanks.:slight_smile:

hello from 2017, but I think you might need an additional flag for reflection to work. Perhaps the property is in the parent class.

You have:

 FieldInfo[] fis = typeof(GUIStyle).GetFields(BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance);

Might need:

 FieldInfo[] fis = typeof(GUIStyle).GetFields(BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance | BindingFlags.FlattenHierarchy);

or even in some cases | BindingFlags.Static (if your variable is static)