GameObject.Find "This function only returns active gameobjects." You can reference inactive objects by using drag'n'drop in the inspector, or by finding active gameobjects and then deactivating them.
↧
Answer by Eric5h5
↧
Answer by Antony Blackett
The solution only works if you don't rely on transform.root anywhere in your game. It also doesn't work if you need to find objects that are children of objects that don't get destroyed on load.
Add a GameObject that is the root of all GameObjects in your scene. Then instead of
FindObjectsOfType()
use
GetComponentsInChildren( typeof(Transform), true );
That should return all transforms of all GameObjects in the scene as they are all a child of the scene root, active or not.
If you can't or don't want to create a scene root object then you'll need to make an array of all the root objects in your scene and all GetCompoenentsInChildren() on all of them separately.
↧
↧
Answer by Bampf
Tranquility's [link he posted in the comments][1] contains an easy solution. Just keep an array of the disabled objects that you might want to find again.
In the given code the author was bringing back all the disabled objects at once, whereas you just need to search the array for the desired object and return it.
To put a nice wrapper around it, you could call this array something like SceneTrash, and when you want to deactivate an object call your own PutInTrash method to deactivate an object and store it in the trash can. Then your code can rummaged through the trashed objects whenever it needs to.
[1]: http://answers.unity3d.com/questions/14178/cannot-toggle-active-on-gameobjects-that-are-inactive
↧
Answer by Antony Blackett
Here's how you do it.
Resources.FindObjectsOfTypeAll(typeof(GameObject)) as GameObject[];
Note this can also return prefabs not just object instances in the scene so be careful when using it at edit time.
↧
Answer by tavoevoe
Make sure you save a reference to the object before you set it to inactive.
↧
↧
Answer by bdawson
This is kind of gross, but it works well:
public static List GetAllObjectsInScene(bool bOnlyRoot)
{
GameObject[] pAllObjects = (GameObject[])Resources.FindObjectsOfTypeAll(typeof(GameObject));
List pReturn = new List();
foreach (GameObject pObject in pAllObjects)
{
if (bOnlyRoot)
{
if (pObject.transform.parent != null)
{
continue;
}
}
if (pObject.hideFlags == HideFlags.NotEditable || pObject.hideFlags == HideFlags.HideAndDontSave)
{
continue;
}
if (Application.isEditor)
{
string sAssetPath = AssetDatabase.GetAssetPath(pObject.transform.root.gameObject);
if (!string.IsNullOrEmpty(sAssetPath))
{
continue;
}
}
pReturn.Add(pObject);
}
return pReturn;
}
↧
Answer by akasurreal
FYI I wrote this and it worked for my purposes, I know it may not work for all. Look up the Unity docs on Resources.FindObjectsOfTypeAll to see some potential pitfalls.
public class Helpers : System.Object
{
public static Object Find(string name, System.Type type)
{
Object [] objs = Resources.FindObjectsOfTypeAll(type);
foreach (Object obj in objs)
{
if (obj.name == name)
{
return obj;
}
}
return null;
}
}
I use it like this:
UIPanel SelectSongsPanel = (UIPanel)Helpers.Find("Panel (Select Songs)", typeof(UIPanel));
SelectSongsPanel.gameObject.SetActiveRecursively(true);
↧
Answer by Cawas
There are at very least 4 options: [`GetChild`](http://answers.unity3d.com/questions/30296/question-regarding-transformgetchild.html), [`GetComponentsInChildren`](http://docs.unity3d.com/Documentation/ScriptReference/GameObject.GetComponentsInChildren.html), [`FindObjectsOfType`](http://docs.unity3d.com/Documentation/ScriptReference/Object.FindObjectsOfType.html?from=GameObject) and [`FindGameObjectsWithTag`](http://docs.unity3d.com/Documentation/ScriptReference/GameObject.FindGameObjectsWithTag.html). We could also use some variations that won't bring an array, for instance. Listed below in no particular order.
1. **GetChild** a method of `Transform`, it still works even today on Unity4, and it's still not in the Docs for whatever reason. It will bring the child be it active or not. Probably the cheapest to use, since we have to use in each immediate parent we want to get the inactive GameObject. It will just be a pain to code and maintain.
1. **GetComponentsInChildren** needs to have a root object. We could set up the scene with just 1 main root here. Very simple to use, but also very heavy. Apply this in the root object:
foreach (Transform child in GetComponentsInChildren(true))`
1. **FindObjectsOfType** doesn't need a root object. Docs say it won't return inactive objects, but it does. Since it's the heaviest listed here and highly unadvised to use, we could do something like:
foreach ( GameObject root in GameObject.FindObjectsOfType(typeof(GameObject)) ) {
if (root.transform.parent == null) { // game object with no parent
// here, iterate through each `root` child using your prefered method
// or simply remove the 'if' above
}
}
1. **FindGameObjectsWithTag** my favourite [one][1], way faster and simpler than all others, but we can't add more than 1 tag per object so it may be prohibitive if we already use tag for something else. It also needs no root, use it from anywhere:
foreach ( GameObject obj in GameObject.FindGameObjectsWithTag("tag") )
Disclaimer: @bdawson actually gave the same solution about FindObjectsOfType and @Antony scratched it, twice. None were specific enough.
[1]: http://answers.unity3d.com/questions/48252/how-to-find-inactive-gameobject.html?page=2#answer-320092
↧
Answer by Stalli
Here I need to find an child inactive object named "CheckPicture" of parent "objectParam".
objectParam.GetComponentsInChildren().FirstOrDefault(component => component.gameObject.name == "CheckPicture");
↧
↧
Answer by Noob_Vulcan
Things that can find inactive gameObjects :
transform.Find() or transform.FindChild()
transform.GetComponentsInChildren(true)
Resources.FindObjectsOfTypeAll()
For more detail you can refer to http://www.unityrealm.com/how-to-find-inactive-gameobject-in-unity/
↧
Answer by RLAWLSGH
public static T[] FindObjectOfTypeIncludeInactivated() where T : Component{
List result = new List();
foreach( GameObject rootObj in UnityEngine.SceneManagement.SceneManager.GetActiveScene().GetRootGameObjects() ) {
Component[] comps = rootObj.GetComponentsInChildren(typeof(T), true);
T[] childObject = Array.ConvertAll(comps, (x) => (T)x);
result.AddRange(childObject);
}
return result.ToArray();
}
In my case this was helpful. (It works on 5.4f +)
↧
Answer by CarterG81
> Does GameObject.Find() work on> inactive objects? If not, how do you> find and reference inactive objects.
GameObject.Find() is only useful (good) in small scenes. Best practice is to avoid using this for any scene with more than a handful of gameobjects (including children).
I find it is best practice to store a reference to every gameobject you create.
How do you keep track of your gameobjects? By name? UniqueGUID? By type?
You could use Dictionaries for this, sorting them by any way you desire.
By name or UniqueGUID & gameobject
Dictionary allObjects;
string myGUID = Guid.NewGuid().ToString();//By Unique GUID
By position & script type
public static Dictionary allTiles = new Dictionary(); //Collection of all Tile GameObjects via Tile.cs script
By name/uniqueID & script type
public static Dictionary allGameWorldObjects = new Dictionary(); //Collection of all GameWorldObjects
public static Dictionary allPlayerObjects = new Dictionary(); //Collection of all PlayerObjects
All objects in array
Gameobject[] AllObjects;
In a list by class
List allGameWorldObjects ; //Holds all GameWorldObjects, PlayerCharacters, & Containers
public class GameWorldObject {}
public class PlayerCharacter : GameWorldObject { }
public class Container : GameWorldObject { }
In a list by gameobject
List allPlayerObjects;
List allGameWorldObjects ;
↧
Answer by bburtson09
You Are looking for Resources.FindObjectsOfTypeAll(),
as Noob_vulcan said.
I wrote some test code and found many solutions, I will share 2 of my solutions the first being a broad implementation that is flexible enough for most projects.
I am using the System.Linq namespace in these examples.
Snippet 1:
var allObjects = Resources.FindObjectsOfTypeAll(typeof(GameObject));
var inactiveObjects = allObjects.Select(p => p as GameObject)
.Where(h => h.activeInHierarchy == true);
foreach (var inactive in inactiveObjects)
{
print(inactive.name);
}
This snippet will return a collection of all inactive Game Objects in the scene and if you try this code you will see that your console output will display a few objects under the hood you didn't know were there.
Snippet 2:
var allObjects = Resources.FindObjectsOfTypeAll(typeof(GameObject));
//if you want to find it by your name similar to GameObject.Find("myGameObjectName")
var myObject = allObjects.Select(p => p as GameObject)
.Where(n => n.name == "myGoName").SingleOrDefault(); //use your gameObjectsName name for your filter predicate
print(myObject.name);
myObject.SetActive(true);
This code will return a single gameObject that matches your predicate string you test against:: in this case "myGoName". When I ran this code I had a tangible reference to my game object that I was able to set back to active which I'm sure means you can manipulate its components and values any way you like.
You might be thinking "this seems suspiciously inefficient", but I want to just say quickly that linq uses something called deferred execution, and if used properly is tremendously efficient. I will not get into the details of the system.linq namespace because it's beyond the scope of this question.
* and can definitely be more efficient than your boilerplate foreach loops.
I hope this helps!
↧
↧
Answer by Eric5h5
GameObject.Find "This function only returns active gameobjects." You can reference inactive objects by using drag'n'drop in the inspector, or by finding active gameobjects and then deactivating them.
↧
Answer by Antony-Blackett
The solution only works if you don't rely on transform.root anywhere in your game. It also doesn't work if you need to find objects that are children of objects that don't get destroyed on load.
Add a GameObject that is the root of all GameObjects in your scene. Then instead of
FindObjectsOfType()
use
GetComponentsInChildren( typeof(Transform), true );
That should return all transforms of all GameObjects in the scene as they are all a child of the scene root, active or not.
If you can't or don't want to create a scene root object then you'll need to make an array of all the root objects in your scene and all GetCompoenentsInChildren() on all of them separately.
↧
Answer by Bampf
Tranquility's [link he posted in the comments][1] contains an easy solution. Just keep an array of the disabled objects that you might want to find again.
In the given code the author was bringing back all the disabled objects at once, whereas you just need to search the array for the desired object and return it.
To put a nice wrapper around it, you could call this array something like SceneTrash, and when you want to deactivate an object call your own PutInTrash method to deactivate an object and store it in the trash can. Then your code can rummaged through the trashed objects whenever it needs to.
[1]: http://answers.unity3d.com/questions/14178/cannot-toggle-active-on-gameobjects-that-are-inactive
↧
Answer by Antony-Blackett
Here's how you do it.
Resources.FindObjectsOfTypeAll(typeof(GameObject)) as GameObject[];
Note this can also return prefabs not just object instances in the scene so be careful when using it at edit time.
↧
↧
Answer by tavoevoe
Make sure you save a reference to the object before you set it to inactive.
↧
Answer by bdawson
This is kind of gross, but it works well:
public static List GetAllObjectsInScene(bool bOnlyRoot)
{
GameObject[] pAllObjects = (GameObject[])Resources.FindObjectsOfTypeAll(typeof(GameObject));
List pReturn = new List();
foreach (GameObject pObject in pAllObjects)
{
if (bOnlyRoot)
{
if (pObject.transform.parent != null)
{
continue;
}
}
if (pObject.hideFlags == HideFlags.NotEditable || pObject.hideFlags == HideFlags.HideAndDontSave)
{
continue;
}
if (Application.isEditor)
{
string sAssetPath = AssetDatabase.GetAssetPath(pObject.transform.root.gameObject);
if (!string.IsNullOrEmpty(sAssetPath))
{
continue;
}
}
pReturn.Add(pObject);
}
return pReturn;
}
↧
Answer by akasurreal
FYI I wrote this and it worked for my purposes, I know it may not work for all. Look up the Unity docs on Resources.FindObjectsOfTypeAll to see some potential pitfalls.
public class Helpers : System.Object
{
public static Object Find(string name, System.Type type)
{
Object [] objs = Resources.FindObjectsOfTypeAll(type);
foreach (Object obj in objs)
{
if (obj.name == name)
{
return obj;
}
}
return null;
}
}
I use it like this:
UIPanel SelectSongsPanel = (UIPanel)Helpers.Find("Panel (Select Songs)", typeof(UIPanel));
SelectSongsPanel.gameObject.SetActiveRecursively(true);
↧