Prefab from List<GameObject> is created twice, but once with no content.

Hello guys please can you help me?

  1. I have my public List where i put my “pages” prefabs before play.
    When i hit play for all these prefabs is created its own page and button - Screen1

  2. Everything work as expected except for some reason i dont know there is also created empty game object in root of scene and i dont know how to get rid of it. - Screen 2

I am 100% sure those “Empty prefabs” are created during this code, can you please explain me why and how can i prevent it?Thanks for advice.

Code :

       void AddLayoutComponents()
        {           
            List<GameObject> pageList = pages.list;
            int i = 0;
            if(pageList.Count > 0)
            {
                foreach(GameObject pagePrefab in pageList)
                {
                    if(pagePrefab != null)
                    {
                        bool isActive = false;
                        if(i.Equals(0))
                        {
                            isActive = true;
                        }
                        var page = Instantiate(pagePrefab, layout.content.transform);
                        page.AddComponent<LayoutComponentBehaviour>().Init(LayoutComponentType.page, isActive, layout.content);
                        page.transform.name = pagePrefab.name;


                        var button = Instantiate(layout.LayoutComponentPrefab, layout.topMenu);
                        button.transform.name = pagePrefab.name;
                        button.GetComponent<LayoutComponentBehaviour>().Init(LayoutComponentType.button, true, layout.content);

                        i += 1;

                    }

                }
            }
            else
            {
                Debug.Log("No pages ale selected.");
            }
        }




It seems a bit strange that you instantiate a prefab and then add another component (your “LayoutComponentBehaviour”). While this is totally possible, the question is always, why isn’t it part of the prefab? Do you need the prefab without it at any time? Your issue may be related to what is happening inside the Init method of that class that you add afterwards.

Just to rule out the obvious: You are sure the method “AddLayoutComponents” is only called once, right? You have added some Debug.Logs to your code to verify that, right?

Note that Debug.Log can take a second “context” argument. This can be any UnityEngine.Object reference. When you pass such a context object, Unity will highlight / ping that object in the hierarchy / project view when you click on the log message in the console. This often helps to identify the objects you’re dealing with. You can log the prefab reference, you can log the instantiated object and click the logs to see if they are actually the correct objects. Of course you can also pass “this” to a log to see which object is actually invoking the method.

1 Like

Thank you for reply.

True is that this could be part of prefab since all pages will be “LayoutComponents”.

Yes i only run it from Start once.

I didnt know that i can try it.But i debugged it before and those objects are created right after Start() and only once.
It looks like it have something to do when i Initialize List in inspectors then those objects are created in root of scene but without its content.

Inside Init method i only set size of layout.

        void Init()
        {
            SetLayoutSize(new float[3] { .1f, .8f, .1f }); //Each value define height of game object, total must equal 1      
        }
        void SetLayoutSize(float[] layoutSizes)
        {
            float[] validatedSizes = Utils.ValidateLayoutSize(layoutSizes);

            float width = layout.canvas.rect.width;
            float height = layout.canvas.rect.height;


            RectTransform[] layouts = new RectTransform[3];
            layouts[0] = layout.topMenu;
            layouts[1] = layout.content;
            layouts[2] = layout.ads;

            for(int i = 0; i < layouts.Length; i++)
            {
                layouts[i].sizeDelta = new Vector2(width, height * validatedSizes[i]);
            }
        }

I was mainly concerned about the Init of LayoutComponentBehaviour which you call explicitly inside the loop. The method you’ve shown seems to be the Init of this script.

Anyways, Unity does never create gameobjects on itself. So there has to be some code (maybe in any script on any part of your prefab) that is creating those gameobjects. If those are just empty gameobjects, are you sure you don’t have a new GameObject("GraphsPage") anywhere in your code? This would create a new empty gameobject with that name.

1 Like

You was right.
Problem was in my code here in Init() in LayoutComponentBehavour - thanks.

     public void Init(LayoutComponentType type,bool isActive,RectTransform contentParent)
        {
            properties = new LayoutComponentProperties(type, gameObject.transform.parent.GetComponent<RectTransform>(),isActive,contentParent);
            gameObject.SetActive(isActive);

            if(properties.type == LayoutComponentType.button)
            {
            Utils.CreatePageButton(gameObject,contentParent);
            }
       
        }