Search Unity

LoadAllAssetsAtPath not working or I'm using it wrong?

Discussion in 'Editor & General Support' started by Leslie-Young, Nov 1, 2011.

  1. Leslie-Young

    Leslie-Young

    Joined:
    Dec 24, 2008
    Posts:
    1,080
    I'm trying to get a list of prefabs so I can place them in the scene via code.
    The code below keeps saying "found: 0" and I have about 20 prefabs in that folder.
    Code (csharp):
    1.  
    2. [MenuItem("Tools/Create Decor")]
    3. public static void KBM_Create_Decor()
    4. {
    5.     // find all the decor related prefabs
    6.     Object[] assets = AssetDatabase.LoadAllAssetsAtPath("Assets/art/tile_decor/");
    7.     Debug.Log("found: " + assets.Length);
    8.     foreach (Object asset in assets)
    9.     {
    10.         Debug.Log(": " + asset.name);
    11.     }
    12. }
    13.  
     
  2. ChiefHawks

    ChiefHawks

    Joined:
    Nov 30, 2011
    Posts:
    1
    Is the script that uses the AssetDatabase in the Assets/Editor folder?

    http://unity3d.com/support/documentation/ScriptReference/AssetDatabase.html
     
  3. jnakai

    jnakai

    Joined:
    Aug 28, 2009
    Posts:
    38
    I'm seeing the same issue, even running AssetDatabase.LoadAllAssetsAtPath("Assets") is returning 0 assets
     
  4. jnakai

    jnakai

    Joined:
    Aug 28, 2009
    Posts:
    38
    Looking at this further, seems LoadAllAssetsAtPath() only works when I directly reference a single asset. Trying to use this to load and return all the assets in a directory doesn't work and returns a 0 length array...annoying
     
  5. probbins

    probbins

    Joined:
    Oct 19, 2010
    Posts:
    216
    I am having the same issue, after reading the documentation again I believe there is no method in AssetBundles to get all assets from a folder.

    LoadAllAssetsAtPath returns a object including all objects inside the object. E.G A Assest may include children such as a mesh, therefor it returns both.

    I believe the documentation could be a little bit clearer!

    As a work around I guess ill just need to use the C# library to return the all file paths at a path. EG http://www.csharp-examples.net/get-files-from-directory/
     
    Last edited: Dec 13, 2011
  6. duke

    duke

    Joined:
    Jan 10, 2007
    Posts:
    763
    Yeah this is quite confusing. It would make more sense if it were re-labeled LoadAllSubAssetsAtPath.
     
  7. B_Nut

    B_Nut

    Joined:
    Apr 14, 2013
    Posts:
    1
    !!!JAVASCRIPT!!!
    Okay I spend a whole day looking for that. In my case I wanted to load a bunch of textures to integrate simple 2D-Animations without changing the script for every new Image (These aren't developed yet). On another (not good tagged) forum.

    The right Command is:
    Code (csharp):
    1. Resources.LoadAll (path : String, systemTypeInstance : Type)
    You should know that you don't have to give the whole path. Just Create a folder at "Assets/Resources/*customfolder*/"
    In my case this works fine:

    Code (csharp):
    1. *global*  var ChangeWalkInterval : float = 0.1;
    2. function ChangeImage(key){
    3.  
    4.         var MarioWalk : Object[];
    5.         if (key == "d")
    6.         MarioWalk = Resources.LoadAll("MarioWalkRight", Texture);
    7.         if (key == "a")
    8.         MarioWalk = Resources.LoadAll("MarioWalkLeft", Texture);
    9.  
    10.         var index : int = Time.time / ChangeWalkInterval;
    11.         index = index % MarioWalk.length;
    12.         renderer.material.mainTexture = MarioWalk[index];
    13. }
    Read the Helpfile for Resources.LoadAll:

    The last lines are copied from here.
     
  8. tomtominc

    tomtominc

    Joined:
    Nov 7, 2013
    Posts:
    21
    I know this is an old topic but this is what I do to get all assets. Is there a better way?

    Code (CSharp):
    1.   /// <summary>
    2.         /// Tries the get an asset.
    3.         /// </summary>
    4.         /// <returns>The asset.</returns>
    5.         /// <param name="optionalName">Optional name: if no name provided returns the first asset.</param>
    6.         /// <typeparam name="T">The 1st type parameter.</typeparam>
    7.         public static T TryGetAsset<T>(string optionalName = "") where T : UnityEngine.Object
    8.         {  
    9.             // Gets all files with the Directory System.IO class
    10.             string[] files = Directory.GetFiles(Application.dataPath, "*.*",SearchOption.AllDirectories);
    11.             T asset = null;
    12.  
    13.             // move through all files
    14.             foreach (var file in files)
    15.             {
    16.                 // use the GetRightPartOfPath utility method to cut the path so it looks like this: Assets/folderblah
    17.                 string path = GetRightPartOfPath(file,"Assets");
    18.  
    19.                 // Then I try and load the asset at the current path.
    20.                 asset = AssetDatabase.LoadAssetAtPath<T>(path);
    21.  
    22.                 // check the asset to see if it's not null
    23.                 if (asset)
    24.                 {
    25.                     // if the optional name is nothing then we skip this step
    26.                     if (optionalName != "")
    27.                     {
    28.                         if (asset.name == optionalName)
    29.                         {
    30.  
    31.                             Debug.Log("Found the database at path: " + path + "with name: " + asset.name);
    32.                             break;
    33.                         }
    34.                     }
    35.                     else
    36.                     {
    37.                         Debug.Log("Found the database at path: " + path);
    38.                         break;
    39.                     }
    40.                 }
    41.  
    42.             }
    43.  
    44.             return asset;
    45.         }
    46.  
    47.         private static string GetRightPartOfPath(string path, string after)
    48.         {
    49.             var parts = path.Split(Path.DirectorySeparatorChar);
    50.             int afterIndex = Array.IndexOf(parts, after);
    51.  
    52.             if (afterIndex == -1)
    53.             {
    54.                 return null;
    55.             }
    56.  
    57.             return string.Join(Path.DirectorySeparatorChar.ToString(),
    58.             parts, afterIndex, parts.Length - afterIndex);
    59.         }
     
  9. the_lemur

    the_lemur

    Joined:
    Apr 3, 2013
    Posts:
    104
    Honestly after all these years Unity documentation continues to be some of the worst I've ever seen.

    The documentation just tends to reiterate the function name itself.

    "Loads assets at the given path."

    Well I have a ton of json files there and not one shows up. And yet using the System.IO File/Directory functions everything becomes EXTREMELY SIMPLE.

    I wrote the whole thing in 5minutes. With AssetDatabase, an hour later.. Nothing. But oh Don't use System.IO they warn you... Usability is just ridiculous.
     
  10. FlightOfOne

    FlightOfOne

    Joined:
    Aug 1, 2014
    Posts:
    473
    It is indeed an old thread yet we are still confused by LoadAllAssetsAtPath() method. See the manual for more info on what it really does.

    Here's what I did to get all the assets (UNITY OBJECTS) from a given folder -figured it would save someone some time and headaches. I mainly use this to add Scriptable objects. Note that this only works in the editor.

    Code (CSharp):
    1. #if UNITY_EDITOR
    2.  
    3.         /// <summary>
    4.         /// Adds newly (if not already in the list) found assets.
    5.         /// Returns how many found (not how many added)
    6.         /// </summary>
    7.         /// <typeparam name="T"></typeparam>
    8.         /// <param name="path"></param>
    9.         /// <param name="assetsFound">Adds to this list if it is not already there</param>
    10.         /// <returns></returns>
    11.         public static int TryGetUnityObjectsOfTypeFromPath<T>(string path, List<T> assetsFound) where T : UnityEngine.Object
    12.         {
    13.             string[] filePaths = System.IO.Directory.GetFiles(path);
    14.  
    15.             int countFound = 0;
    16.  
    17.             Debug.Log(filePaths.Length);
    18.  
    19.             if (filePaths != null && filePaths.Length > 0)
    20.             {
    21.                 for (int i = 0; i < filePaths.Length; i++)
    22.                 {
    23.                     UnityEngine.Object obj = UnityEditor.AssetDatabase.LoadAssetAtPath(filePaths[i], typeof(T));
    24.                     if (obj is T asset)
    25.                     {
    26.                         countFound++;
    27.                         if (!assetsFound.Contains(asset))
    28.                         {
    29.                             assetsFound.Add(asset);
    30.                         }
    31.                     }
    32.                 }
    33.             }
    34.  
    35.             return countFound;
    36.         }
    37.  
    38. #endif
     
    id0, Rodolfo-Rubens, sama-van and 4 others like this.
  11. SoulGameStudio

    SoulGameStudio

    Joined:
    Jan 18, 2016
    Posts:
    46
    FlightOfOne likes this.
  12. illinar

    illinar

    Joined:
    Apr 6, 2011
    Posts:
    812
    Just stumbled into it. Very unfortunate method naming.
     
  13. zachstronaut

    zachstronaut

    Joined:
    Jan 30, 2016
    Posts:
    3
    Unity maybe can't/won't do anything about the method naming at this point, but they sure could update the documentation page for this method to explain that if you want to get all assets of a type from a folder you can't use this method. They could even provide an example of how you could do it. Like this thread provides.
     
  14. echoAndecho

    echoAndecho

    Joined:
    Aug 27, 2019
    Posts:
    1
    I knew it! Bad documentation for this one. Same here, just stumbled onto this thread.

    Another reminder for Unity to work harder on the Doc.
    Will use .Net's System.IO instead.
     
unityunity