I’m trying to get all the children gameObjects,
from an Empty parent to which I have applied a script,
so I can act on each of the children with the same script.
I’m trying to get all the children gameObjects,
from an Empty parent to which I have applied a script,
so I can act on each of the children with the same script.
See the Transform
docs for API details. I’ll provide two examples below.
The fact that
Transform
works withforeach
is not well documented, but Transform implementsIEnumerable
whichforeach
uses. The current (Unity 4.3.1f1)IEnumerable
implementation thatTransform
provides is callingchildCount
andGetChild
on each iteration. A curious reader can check this themselves by navigating to theTransform
class in MonoDevelop where the decompiled source is readable in the Assembly Browser.
To explain the same thing another way:
You’d expect that with Transform
, Unity would offer a call such as, say, “allChildren”. So you’d do something like:
foreach (Transform child in transform.allChildren() { . . .
However, Unity do not do that. For better or worse, they make “transform” magically supply “all of its children” when it is in a situation such as a foreach.
So somewhat confusingly, you only have to write:
foreach (Transform child in transform) { . . .
using UnityEngine;
public class PrintChildren : MonoBehaviour
{
void Start()
{
WithForeachLoop();
WithForLoop();
}
void WithForeachLoop()
{
foreach (Transform child in transform)
print("Foreach loop: " + child);
}
void WithForLoop()
{
int children = transform.childCount;
for (int i = 0; i < children; ++i)
print("For loop: " + transform.GetChild(i));
}
}
If you wanted to get the game objects of the children (which will be the Transforms, not the GameObjects), just access gameObject
of the child Transform
in each iteration.
I believe you are looking for GetComponentsInChildren(). There is an example on the reference page. A couple of notes:
Your code will be something like:
yourScripts = GetComponentsInChildren<YourScriptName>();
foreach (YourScriptName yourScript in yourScripts) {
yourScript.DoSomething();
}
If you want to get every single child transform of a transform use:
List<Transform> GetAllChilds(Transform _t)
{
List<Transform> ts = new List<Transform>();
foreach (Transform t in _t)
{
ts.Add(t);
if (t.childCount > 0)
ts.AddRange(GetAllChilds(t));
}
return ts;
}
Thanks for the tip! After some fiddling, here’s a slightly cleaner version. It doesn’t return the parent itself.
static List<Transform> GetAllChildren(Transform parent, List<Transform> transformList = null)
{
if (transformList == null) transformList = new List<Transform>();
foreach (Transform child in parent) {
transformList.Add(child);
GetAllChildren(child, transformList);
}
return transformList;
}
Note, to make it back to an extension method do this:
public static class TransformExtension {
public static List<Transform> GetAllChildren(this Transform parent, List<Transform> transformList = null)
{
if (transformList == null) transformList = new List<Transform>();
foreach (Transform child in parent) {
transformList.Add(child);
child.GetAllChildren(transformList);
}
return transformList;
}
}
Here is a Transform extension based on the answer
using UnityEngine;
public static class TransformExtensions {
/**
* <summary>Gets the child transforms on first level</summary>
* <example>
* Transform[] t = transform.GetFirstChildTransforms();
* for ( int i = 0; i < t.Length; i++ )
* {
* t[ i ].GetComponent<UI_Element>().Refresh();
* }
* </example>
* <see cref="https://answers.unity.com/questions/594210/get-all-children-gameobjects.html"/>
*
* */
public static Transform[] GetFirstChildTransforms(this Transform tran )
{
int children = tran.childCount;
Transform[] r = new Transform[children];
for ( int i = 0; i < children; ++i )
{
r[ i ] = tran.GetChild( i );
}
return r;
}
}
For the lazy boi :
public static class ClassExtension
{
public static List<GameObject> GetAllChilds(this GameObject Go)
{
List<GameObject> list = new List<GameObject>();
for (int i = 0; i< Go.transform.childCount; i++)
{
list.Add(Go.transform.GetChild(i).gameObject);
}
return list;
}
}
Later in you can you can simply Call this :
gameobjet.GetAllChilds()
how can I use this code?
List<Transform> children = TransformExtension.GetAllChildren();
returns an compiler error [CS1501]: No overload for method GetAllChildren' takes
0’ arguments in Custom\Scripts..\objects-analysis.cs at [88, 55]
This gets all children no matter the depth
foreach (var childTransform in GetComponentsInChildren<Transform>())
{
childTransform.gameObject....
}
probably not an efficient way, but you shouldn’t be doing this in an update anyway.