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 VincentBlaser · Jul 18, 2018 at 07:00 AM · scripting problemerrorinstantiatenullreferenceexception

After Instantiating a Prefab I get a NullReference Error even though the Object was created

So I don´t know if I´m missing an dumb error of myself but my problem is: I´ve got an class which deserializes a json file into a tree-structure. That part is working without an error. Now while doing this i want to create Objects of another class - we just call it "CityObject" for the moment.

 public class CityObject : MonoBehaviour {
  
     private GameObject gameObject;
  
     public ArrayList children;
  
     public int width;
  
  
     public CityObject(GameObject prefab, int newWidth)
     {
         gameObject = Instantiate(prefab);
         children = new ArrayList();
         width = newWidth;
     }
 }

Depending on the Information in the json file, the GameObject should get a simple cube prefab or a flat cube prefab and instantiate it. So far so good - in the unity Scene all Objects are created, so in my example there are 5 created GameObjects - 2 flat and 3 simple cubes. Code (CSharp):

 public class CityBuilder : MonoBehaviour {
  
     public GameObject plane;
     public GameObject cube;
     public CityObject origin;
  
     private int maxW = 0;
  
     private ProjectView ProcessProjectData(string jsonString)
     {
         ProjectView parsejson = JsonUtility.FromJson<ProjectView>(jsonString);
         return parsejson;
     }
  
     private GameObject FindPrefab(string type)
     {
         switch (type.ToLower())
         {
             case "block": newPlane = false; return cube;
             case "scope": newPlane = true; return plane;
             default: return null;
         }
     }
    
     private CityObject CreateGameObjectFromProjectData(ProjectData projectData, CityObject cityObjectParent)
     {
      
         var prefab = FindPrefab(projectData.type);
         if (!prefab)
             return null;
  
  
         CityObject rootCityObject = new CityObject(prefab,  getSubtreeWidth(projectData));
  
        
         if(maxW == 0)
         {
             maxW = rootCityObject.width;
         }
         scaleObject(rootCityObject);
        
         /* * *
          * If an object has one or more children, then the children should execute this method on their own.
          */
  
         if (projectData.children != null)
         {
             foreach (ProjectData data in projectData.children)
             {
                 Debug.Log(data.id);
             }
             foreach (ProjectData data in projectData.children)
             {
                 CityObject newChild = CreateGameObjectFromProjectData(data, rootCityObject);
                 rootCityObject.appendChild(newChild);
             }
         }
         return rootCityObject;
     }

The problem is that in line 40 i want to scale the gameObject of the cityObject like this:

 private void scaleObject(CityObject node)
 
     {
 
         float scaleRatio = (float)(node.width/maxW);
 
         node.gameObject.transform.localScale.Set(scaleRatio, scaleRatio, scaleRatio);
 
     }

Then there is a NullReference Error for the node.GameObject - so there seems to be no reference between the cityObject and the GameObject. This is the part i can´t understand. Is it the Instantiate in the CityObejct Constructor? Isn´t the Instantiate creating a Reference between the "Script-Object" and the Gameobject in the unity-Scene?

Just for explanation. I don´t want to create a GameObject in the scene which should get the "CityObject" Component. What i wanna do is creating an CityObject (just in code) and this CityObject has a "gameObject" attribute which is basically just a real GameObject in the scene. After creating it, i still want to change the GameObject. I want to scale it and later on i want to reposition it but when I try to access it, there´s the NullReference Error.

Comment
Add comment · Show 4
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 VincentBlaser · Jul 18, 2018 at 07:34 AM 0
Share

What i forgot to mention: When i write a "scale method" in the CityObject class itself, i can scale the gameObject without a problem. The error just occurs if i try to access the gameObject in the "Citybuilder" class.

avatar image Hellium · Jul 18, 2018 at 07:36 AM 0
Share

I don´t want to create a GameObject in the scene which should get the "CityObject" Component.

Then, why CityObject derives from $$anonymous$$onoBehaviour? You should not have a constructor in a deriving from $$anonymous$$onoBehaviour.

avatar image tormentoarmagedoom · Jul 18, 2018 at 07:43 AM 0
Share

Why define a variable with name gameObject?

So confusing... gameObject is a public variable from all objects in the scene... this will only create chaos...

And then you say the gameObject containing this script = NEw instance of object prefab...

CHAOS!

gameObject = Instantiate(prefab);

avatar image VincentBlaser tormentoarmagedoom · Jul 18, 2018 at 07:46 AM 0
Share

Okay sorry i thought i can just quickly point out the main points of the idea and the problem and didn´t care about the names. The names will surely be changed.

Edit: This chaos i created (while trying to be as simple as i can) even was the issue. So I will definitely remember this dumb mistake next time!

2 Replies

· Add your reply
  • Sort: 
avatar image
1

Answer by Bunny83 · Jul 18, 2018 at 08:34 AM

There are countless things wrong in your code ^^.


Lets start with the most important ones:

First of all all components (which include any classes derived from MonoBehaviour) have to be created with AddComponent. They can not be created with "new". Components have a native code counter part in the C++ engine core which would be missing when you create such a class with new. Such a class would be a fake-null object (see the link at the end). As it's not attached to a gameobject it just doesn't work at all.


Since MonoBehaviours can only be created through AddComponent you can't have custom constructors for those classes. Using a constructor on MonoBehaviours is generally not recommended as the actual object creation happens on a seperate thread where you can't use the Unity API.


It looks like your "CityObject" is more like a management class that isn't attached to a gameobject so it probably shouldn't be derived from MonoBehaviour at all.


Unity's JsonUtility (or serialization system in general) has very limited capabilities. It can not serialize / deserialize tree structures. As you know JSON does not support any type information to be stored in the actual json data, so polymorphism also isn't possible.


Next, this line doesn't work as you might think:

 node.gameObject.transform.localScale.Set(scaleRatio, scaleRatio, scaleRatio);

localScale is a property of a value type. What you're doing here is invoking the getter of the property and then you modify the temporary copy of the vector3 value. This will have no effect on the actual scale of the object which is stored on the native side. In order to change the scale you have to invoke the setter of the property. i.e. you have to assign a vector3 value to the localScale property. In your case you can just do:

 node.gameObject.transform.localScale = Vector3.one * scaleRatio;


The "JsonUtility" is quite limited as i said. If you want to design a flexible Json format you want to use another Json parser. I've created SimpleJSON which just reads the json data into data container classes for further processing. I've also made an extension specifically for Unity to read and write some of the most common Unity types (Vector2/3/4, Quaternion, Rect, RectOffset, Matrix4x4). However there are other third party solutions as well.


Some minor things you may want to change:
The ArrayList class is an old pretty much deprecated left over class from times before generics were a thing in C# / .NET / Mono. It's generally adviced to not use it anymore. It stores untyped "object" references and always require casting when accessing elements.


For more information about the serialization issues with Unity's serialization system have a look at this documentation as well as this important blog post

Comment
Add comment · 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
0

Answer by Sonky108 · Jul 18, 2018 at 07:35 AM

I would rather not use constructors while inheriting from MonoBehaviour. See the link below: https://answers.unity.com/questions/862032/c-constructor-in-monobehaviour.html

Also it could be ambiguous gameObject since every MonoBehaviour already have field called gameObject. Probably you are hiding it with new field and then assigning new GameObject to the base one?

Comment
Add comment · Show 3 · 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 VincentBlaser · Jul 18, 2018 at 07:55 AM 0
Share

Also it could be ambiguous gameObject since every $$anonymous$$onoBehaviour already have field called gameObject. Probably you are hiding it with new field and then assigning new GameObject to the base one?

Seems like this really was the issue.. I changed the name and it worked out. Sad that in the end it really was such a dumb mistake Thank you
avatar image Sonky108 VincentBlaser · Jul 18, 2018 at 08:06 AM 0
Share

Glad it helped. Even though it works now I would suggest to refactor the code and don't use constructors while inheriting from $$anonymous$$onoBehaviour

avatar image Bunny83 VincentBlaser · Jul 18, 2018 at 08:38 AM 0
Share

No, you're drawing false conclusions here. Yes your particular null ref error was probably the hiding if the gameObject property of the Component class. However you should have a look at my answer.


btw.: I've reopened your question for two reasons: First I've already written my answer and you just closed the question right before i could post it. Second you closed it with the reason that you accepted the right answer but no answer was accepted.

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

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

Simultaneous Null Reference Exception and expected value 1 Answer

Instantiating class creating copies with same instance ID of 0 0 Answers

NullReferenceException and m_InstanceID == 0 on LoadLevel (C#) 1 Answer

[Closed]NullReferenceException on Object Instantiation onto game world 2 Answers

NullReferenceException 3 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