Wayback Machinekoobas.hobune.stream
May JUN Jul
Previous capture 12 Next capture
2021 2022 2023
1 capture
12 Jun 22 - 12 Jun 22
sparklines
Close Help
  • Products
  • Solutions
  • Made with Unity
  • Learning
  • Support & Services
  • Community
  • Asset Store
  • Get Unity

UNITY ACCOUNT

You need a Unity Account to shop in the Online and Asset Stores, participate in the Unity Community and manage your license portfolio. Login Create account
  • Blog
  • Forums
  • Answers
  • Evangelists
  • User Groups
  • Beta Program
  • Advisory Panel

Navigation

  • Home
  • Products
  • Solutions
  • Made with Unity
  • Learning
  • Support & Services
  • Community
    • Blog
    • Forums
    • Answers
    • Evangelists
    • User Groups
    • Beta Program
    • Advisory Panel

Unity account

You need a Unity Account to shop in the Online and Asset Stores, participate in the Unity Community and manage your license portfolio. Login Create account

Language

  • Chinese
  • Spanish
  • Japanese
  • Korean
  • Portuguese
  • Ask a question
  • Spaces
    • Default
    • Help Room
    • META
    • Moderators
    • Topics
    • Questions
    • Users
    • Badges
  • Home /
avatar image
1
Question by Glurth · Feb 17, 2018 at 08:09 PM · arraycustom editorenablepropertydrawerserializedproperty

Custom Editor/Custom Property Drawer combo, breaks Enable button

I have created a custom Property Drawer, which works fine when the MonoBehavior holding it uses the default Inspector. However, when I try to use a custom Editor, that display nothing but this property drawer: the enable button for the MonoBehavior no longer works properly!

I'm not sure what I could be doing to cause such an issue. Since it works using the default inspector, this lead me, initially, to believe the problem lay with my CustomEditor, and not the property drawer itself.

But further testing shows the custom editor ONLY messed up the Enabled button, if CustomProperty Drawer needs to take some particular action. (It should do this action even for the standard inspector, so I'm not sure why it's behaving differently.)

In particular, the CustomProperty drawer needs to build an array of strings, in a sub-property of the SerializedProperty. When I remove this array-rebuild section, as a test, the enabled button works property (but changes are not stored). This particular section is noted in the custom property drawer code below (near the bottom). I note again, this actually seems to work fine, the ONLY issue is that it breaks the enabled button when used in a custom editor.

What am I doing wrong? How can I resolve this issue? Why do I get different effect (eg. enable button) for the property drawer when using a custom Editor vs the standard Inspector?

OptionNames.cs

 //!This class has a custom property drawer
 [Serializable]
 public class OptionNames
 {
     public string[] selectedOptionNames;  
     public string[] fullList;
 }

TestMono.cs

 [ExecuteInEditMode] //just so we can see debug log post when enabled state changes
 public class TestMono : MonoBehaviour {

    public OptionNames options;// the only member of this class, public and displayed in inspector

    private void Reset()
    {
        Debug.Log("reset");
        options = new OptionNames();
        options.fullList = new string[4] { "a", "b", "c", "d" };
        options.selectedOptionNames = new string[2] { "a", "d" };
    }
    private void OnEnable() { Debug.Log("enabled"); }
    private void OnDisable() { Debug.Log("disabled");  }
 }

TestMonoEditor.cs

 [CustomEditor(typeof(TestMono))]
 public class TestMonoEditor : Editor{
 
     public override void OnInspectorGUI()
     {
         SerializedProperty options = serializedObject.FindProperty("options");
         EditorGUILayout.PropertyField(options, new GUIContent("options"));
         serializedObject.ApplyModifiedProperties();  //stack traces of the debug.Log commands in the monobehavior show this line is invoking the enable state toggle BACK to the state it was before I clicked it.
     }
 }

OptionNamesDrawer.cs

 [CustomPropertyDrawer(typeof(OptionNames))]
 public class OptionNamesDrawer : PropertyDrawer
 {   
     public override void OnGUI(Rect position, SerializedProperty property, GUIContent label)
     {
            
         SerializedProperty listprop;
         SerializedProperty fullListProp;
 
         listprop=property.FindPropertyRelative("selectedOptionNames");
         //get the full list from the serialized object, as a simple string[]
         fullListProp = property.FindPropertyRelative("fullList");
         string[] fullList = new string[fullListProp.arraySize];
         for(int i=0;i<fullList.Length;i++)
         {
             fullList[i]=fullListProp.GetArrayElementAtIndex(i).stringValue;
         }
        
         StringListAsMaskProperty(position, listprop, label, fullList);
     }
 
         //! The SerialedProperty is an array of strings containing only the selected Items.
     public static void StringListAsMaskProperty(Rect r, SerializedProperty prop, GUIContent label, string[] fullList)
     {
         if (fullList == null) return;
         if (prop == null) return;
         int mask = 0;
         int len = prop.arraySize;
         for (int i = 0; i < len; i++)
         {
             string s = prop.GetArrayElementAtIndex(i).stringValue;
             for (int j = 0; j < fullList.Length; j++)
             {
                     
                 if (fullList[j] == s)
                 {
                     mask = mask | (1 << j);
                 }
             }
         }
         mask = EditorGUI.MaskField(r, label, mask, fullList);
 
         //return;   // returning here allows enable state to work
         prop.ClearArray();
         
         int count = 0;
         for (int j = 0; j < fullList.Length; j++)
         {
             if ((mask & (1 << j)) != 0)
             {
                 prop.InsertArrayElementAtIndex(count);// removing this allows enabled state to work!  (remark out clear array above, to keep the list from becomeing empty- changes wont work though, obviously)
                 prop.GetArrayElementAtIndex(count).stringValue = fullList[j];
                 count++;
             }
         }
 
     }
  
 }//end optionNamesDrawer class
Comment
Add comment
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users

1 Reply

· Add your reply
  • Sort: 
avatar image
2
Best Answer

Answer by ElijahShadbolt · Feb 18, 2018 at 12:03 AM

SerializedObject.ApplyModifiedProperties() works in conjunction with SerializedObject.Update().

In your TestMonoEditor.OnInspectorGUI method:

 serializedObject.Update();
 
 SerializedProperty options = serializedObject.FindProperty("options");
 EditorGUILayout.PropertyField(options, new GUIContent("options"));
 
 serializedObject.ApplyModifiedProperties();
Comment
Add comment · Show 2 · Share
10 |3000 characters needed characters left characters exceeded
▼
  • Viewable by all users
  • Viewable by moderators
  • Viewable by moderators and the original poster
  • Advanced visibility
Viewable by all users
avatar image Glurth · Feb 18, 2018 at 01:37 AM 1
Share

That resolved it, thank you.

avatar image Glurth · Feb 19, 2018 at 01:21 AM 1
Share

Did a bit more testing after the solution above worked. I was wondering "well why didn't the other fields/properties I use (not in example script above), cause the same issue? Turns out, the reason this was an issue here because I was CHANGING the serialized property EVERY TI$$anonymous$$E the property drawer was invoked. If it's not changed every time, it appears, the serializedObject.Update() is not absolutely necessary for it to work. As I test: I removed the Update command fix, and changed the $$anonymous$$askField line to this:

 int new$$anonymous$$ask= EditorGUI.$$anonymous$$askField(r, label, mask, fullList);
 if ( (new$$anonymous$$ask & mask) == mask) return;
 mask = new$$anonymous$$ask;

So that it would only rebuild the list IF there was an actual change made by the user. This ALSO resolved the issue.

Your answer

Hint: You can notify a user about this post by typing @username

Up to 2 attachments (including images) can be used with a maximum of 524.3 kB each and 1.0 MB total.

Follow this Question

Answers Answers and Comments

86 People are following this question.

avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image avatar image

Related Questions

CustomPropertyDrawer undoable properties 1 Answer

SerializedProperty isn't being detected as an array? 1 Answer

Custom Editor + Array = A Long Nightmare ! 1 Answer

SerializedObject.FindProperty returning null 2 Answers

Property Drawer SerializedProperty is null 2 Answers


Enterprise
Social Q&A

Social
Subscribe on YouTube social-youtube Follow on LinkedIn social-linkedin Follow on Twitter social-twitter Follow on Facebook social-facebook Follow on Instagram social-instagram

Footer

  • Purchase
    • Products
    • Subscription
    • Asset Store
    • Unity Gear
    • Resellers
  • Education
    • Students
    • Educators
    • Certification
    • Learn
    • Center of Excellence
  • Download
    • Unity
    • Beta Program
  • Unity Labs
    • Labs
    • Publications
  • Resources
    • Learn platform
    • Community
    • Documentation
    • Unity QA
    • FAQ
    • Services Status
    • Connect
  • About Unity
    • About Us
    • Blog
    • Events
    • Careers
    • Contact
    • Press
    • Partners
    • Affiliates
    • Security
Copyright © 2020 Unity Technologies
  • Legal
  • Privacy Policy
  • Cookies
  • Do Not Sell My Personal Information
  • Cookies Settings
"Unity", Unity logos, and other Unity trademarks are trademarks or registered trademarks of Unity Technologies or its affiliates in the U.S. and elsewhere (more info here). Other names or brands are trademarks of their respective owners.
  • Anonymous
  • Sign in
  • Create
  • Ask a question
  • Spaces
  • Default
  • Help Room
  • META
  • Moderators
  • Explore
  • Topics
  • Questions
  • Users
  • Badges