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
0
Question by S_Darkwell · Jun 25, 2016 at 08:14 PM · c#editorarrayinspectorserializedproperty

Insert new custom class element with _default_ values to a SerializedProperty array?

In a custom inspector, I am adding a new custom class "DSReaction" element to a native array named "reactions" obtained via a SerializedProperty. To add the new element to the "reactions" array, I'm using the "InsertArrayElementAtIndex" function.

Here is a stripped-down version of the code:

 using UnityEditor;
 
 [CustomEditor(typeof(DSReacter))]
 public class DSReacterEditor : Editor
 {
     private DSReacter T;
     private SerializedObject Reactor;
         
     private SerializedProperty reactions;
 
     private void OnEnable()
     {
         T = target as DSReacter;
     
         Reactor = new SerializedObject(T);
             
         reactions = Reactor.FindProperty("reactions");
     }
         
     public override void OnInspectorGUI()
     {
         Reactor.UpdateIfDirtyOrScript();
         
         if (GUILayout.Button("New Reaction"))
         reactions.InsertArrayElementAtIndex(0);
                 
         Reactor.ApplyModifiedProperties();
     }
 }

Unfortunately, if the array is not empty, this automatically creates the new element using the variable valuables of the preceding element.

How can I add a new element, but have it retain the default class variable values, as opposed to the values of the preceding element?

Thank you in advance, and be well!

- S.

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
1
Best Answer

Answer by Bunny83 · Jun 25, 2016 at 09:32 PM

That's not possible using SerializedObject / Property. "InsertArrayElementAtIndex" works the same way as the default inspector. When you change the "size" of an array the new values at the end are initialized with the last element in the array. The serialization system doesn't seem to offer a way to initialize an object instance with default values.

The only alternative would be to access the target object manually and modify the array yourself.

Since you already use the target property you should be able to do the following. Note since you did not provide your "DSReacter" class nor your custom data class i can only assume that the "reactions" variable is a native array:

 if (GUILayout.Button("New Reaction"))
 {
     Undo.RecordObject(T, "Added Reaction");
     var list = new List<YourCustomClass>(T.reactions);
     list.Add(new YourCustomClass());
     T.reactions = list.ToArray();
 }

Note the Undo.RecordObject is required or the editor won't detect the changes.

Comment
Add comment · Show 6 · 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 S_Darkwell · Jun 25, 2016 at 09:56 PM 0
Share

@Bunny83: Yes, you assumed correctly that T.reactions is a native array.

I had presumed that I was overlooking a method offered by SerializedProperty. Glad to know that it was the lack of a method as opposed to my inability to locate one.

Thank you for your response and example. I've tested it, and it works perfectly.

Additionally, I've updated my original post to clarify it for future reads based on your comment.

Thank you again, and be well!

- S.

avatar image Bunny83 S_Darkwell · Jun 25, 2016 at 10:28 PM 1
Share

Yes, the SerializedProperty is lacking some important features. This is due to the fact how the serialization system is implemented. It actually doesn't care about class instances as it's only build on top of the actual data that get saved. The fields of a custom class get serialized in a "flattend array fashion". So from the serialization system's point of view only the serialized properties exist. If you have two or more nested custom classes it's a pain to modify or access any of those custom class values through a SerializedObject / Property. It's not possible to get access to an actual instance of a custom class through the serialization system. You would have to go through the actual target / targets reference.

avatar image S_Darkwell Bunny83 · Jun 26, 2016 at 10:58 AM 0
Share

@Bunny83: That makes perfect sense. I'm familiar enough with accessing properties via target and manually registering them in Undo. SerializedProperty's features are far newer to me (though I've been using them for a while). $$anonymous$$y primary concern is the need to make variables accessible through target public, therefor di$$anonymous$$ishing my efforts for making them immutable.

avatar image Plattinator · Jun 26, 2016 at 02:11 AM 0
Share

Wouldn't it be possible to do something like

 reactions.InsertArrayElementAtIndex(0);
 reactions.GetArrayElementAtIndex(0).objectReferenceValue = new Reaction();


ins$$anonymous$$d?

avatar image S_Darkwell Plattinator · Jun 26, 2016 at 11:01 AM 0
Share

@Plattinator: Good question!

That's was actually the avenue I was exploring, but continuously found myself at a dead end.

Using variants of your code, I receive the error: "Cannot convert source type 'DSReaction' to target type 'UnityEngine.Object'."

avatar image Bunny83 Plattinator · Jun 26, 2016 at 11:14 AM 1
Share

No, that's not possible because the "objectReferenceValue" only works for references between assets. The type of objectReferenceValue is not System.Object but UnityEngine.Object. So you can only handle references to other serialized objects with that. Things like references to GameObjects or other $$anonymous$$onoBehaviours

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

167 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 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

How to change inspector with non-Monobehaviour objects ? 1 Answer

Can a GameObject inside of an array be made "accessible" from the editor? 2 Answers

How to access elements in an array through a SerializedProperty? 1 Answer

ReImport in c# of GameObjects only for Scene Objects, not assets? 1 Answer

How do I find the farthest verts of a mesh relative to its object position and store them in an array 1 Answer


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