Search Unity

How to "Get" prefabs from project View by code

Discussion in 'Editor & General Support' started by FiveFingers, Jan 5, 2010.

  1. FiveFingers

    FiveFingers

    Joined:
    Oct 15, 2009
    Posts:
    541
    How do I instantiate a prefab in the Assets folder (.prefab) but not an already present in scene one ?

    From code as far as I could get, I got the prefab in scene with

    Code (csharp):
    1.  
    2. myObj = GameObject.Find("NameOfThePrefab");
    3. myClone = Instantiate(myObj, transform.position, transform.rotation);
    4.  
    but this gets me only the prefab already in scene, not the one in the assets.

    If I remove from the scene the manually dragged instance, the code breaks, and returns me a Null reference exception on the line trying to Find("prefabname").


    I tried also renaming differently the Project prefab, and "looking" for that one, with Find, but no luck!

    I really don't want to waste a draw call or even a gameobject memory allocation for a prefab that I could instantiate directly from the Assets folder.
    Perhaps I got it all wrong, and this simply cannot be done. And I MUST instantiate before the prefab in scene...

    If is possible, how do I write the same operation with an Assets prefab ?

    I'm using unity iphone though, but I think the mechanism should be the same...


    I ask this, because after 4 months development, I discovered that I don't like to have gameobjects with other Transform or GameObjects assigned through a panel. This is hassle when you have many levels/scenes, and every time you have to link back dozens of objects in dozens of scripts vars. Much better do a GameObject.Find at Start/Awake and getting the name, unfortunately this is working for me only with prefabs already present in scene.

    From Unity iPhone documentation, I read:



    Code (csharp):
    1.  
    2. var wreck : GameObject;
    3.  
    4. // As an example, we turn the game object into a wreck after 3 seconds automatically
    5. function Start () {
    6.     yield WaitForSeconds(3);
    7.     KillSelf();
    8. }
    9.  
    10. // Calls the fire method when holding down ctrl or mouse
    11. function KillSelf () {
    12.     // Instantiate the wreck game object at the same position we are at
    13.     var wreckClone = Instantiate(wreck, transform.position, transform.rotation);
    14.  
    15.     // Sometimes we need to carry over some variables from this object
    16.     // to the wreck
    17.     wreckClone.GetComponent(MyScript).someVariable = GetComponent(MyScript).someVariable;
    18.  
    19.     // Kill ourselves
    20.     Destroy(gameObject);
    21. }

    But
    Code (csharp):
    1. var wreck : GameObject;
    Implies that I choose from a crazy pulldown with 1820 objects the proper one every time! (for every scene o for every prefab I put in a scene which carries a script which references to the Wreck object)

    What is the way to "Get" or "Find" the objects in Assets ??


    Thanks in advance for the help,




    Tommaso Lintrami
    Breakdown Studios
     
  2. FiveFingers

    FiveFingers

    Joined:
    Oct 15, 2009
    Posts:
    541
    Whooops I possibly answered my self...

    Are the EditorUtility.FindAsset EditorUtility.InstantiatePrefab

    Code (csharp):
    1.  
    2. static function FindAsset (path : string, type : Type) : Object
    3. static function InstantiatePrefab (target : Object) : Object

    The functions I should look at ?

    Maybe not...because I'd need this at runtime...
     
  3. JDonavan

    JDonavan

    Joined:
    Oct 3, 2009
    Posts:
    105
  4. cj-currie

    cj-currie

    Joined:
    Nov 27, 2008
    Posts:
    337
    Actually, what you probably want is Resources.Load(path : String), where path begins at Assets/Resources.
     
  5. chicknstu

    chicknstu

    Joined:
    May 4, 2010
    Posts:
    11
    Did you get an answer to this?

    No it doesn't. That link tells you how to drag a prefab onto a game object to reference it, not how to get it by name from the list of assets in the project view.

    I've looked around for ages for this and can't find an answer either, sure it's simple!

    This should explain the problem entirely...

    Code (csharp):
    1. var position = Vector3(Random.Range(-6, 6), 0, 12);
    2. Instantiate(IWantToTypeAPrefabNameInHere, position, Quaternion.identity);
     
  6. GibTreaty

    GibTreaty

    Joined:
    Aug 25, 2010
    Posts:
    792
    It has already been answered.

    Code (csharp):
    1.  
    2. Instantiate(Resources.Load("PrefabName"), position, rotation)
    3.  
    Also, the Prefab has to be in a folder named Resources which can be anywhere. Example
    > Prefabs> Resources> PrefabName
     
    Last edited: Apr 6, 2011
  7. Deleted User

    Deleted User

    Guest

    Thanks GibTreaty, this solved my issue.

    My goal was to persist the LeapUnityBridge since it would blow up when it's objects get recreated from a LevelReload. So I then added DontDestroyOnLoad to the LeapUnityBridge. The led to LeapUnityBridge being recreated on each LevelReload which also wasn't good, though it didn't really break anything.

    Code (csharp):
    1.  
    2. public class LeapUnitySingleton : MonoBehaviour
    3. {
    4.     void Awake()
    5.     {
    6.         // see if the object exists, if not, instantiate it
    7.         var theObject = GameObject.Find("LeapUnityBridge(Clone)");
    8.    
    9.         if (theObject == null)
    10.         {
    11.             Instantiate(Resources.Load("LeapUnityBridge"),Vector3.zero, Quaternion.identity);
    12.         }
    13.     }
    14. }
    15.  
    Also thanks to MatthewJCollins http://forum.unity3d.com/threads/41233-Trouble-with-DontDestroyOnLoad-(-) for the singleton awake method.

    Anyone with suggested improvements?
     
    GibTreaty likes this.
  8. erudd

    erudd

    Joined:
    Sep 17, 2015
    Posts:
    1
  9. Helbold

    Helbold

    Joined:
    Jan 16, 2016
    Posts:
    2
    I ran into the same problem. I designed a method on my GameControl Script to Instanciate any Object if it needs Respawn.
    Those lines solved the problem with those prefabs:

    C#
    1. //This overloaded Version of the Method pretty much copies the Original
    2. GameObject New_Object = Instantiate<GameObject>(Original_Object);
    3. //Cleanup
    4. GameObject.Destroy(Original_Object);

    5. //Check for Activation
    6. if (!New_Object.activeSelf)
    7. {
    8. New_Object.SetActive(true);
    9. }
    I ended up having a new GameObject with the name of the old one + "(Clone)".
    Anyway, all components are set up and working.
     
    FerdowsurAsif likes this.