- Home /
How to access a child input field from a parent prefab script.
I have a the following hierarchy transformed into a prefab:
equipmentEditionScreen (Panel) > Edition Panel (Panel) > Parameters Scroll View (Panel) > Content > Parameters Scroll View Content (empty GameObject) > Basic Properties Label > Number Of Elements Input Field.
A script attached to the Edition Panel has the following code:
InputField numberOfElementsInputField;
...
void StartInputFields () {
RectTransform[] rectTrans = GetComponentsInChildren<RectTransform> ();
foreach (RectTransform trans in rectTrans) {
if (trans.name = "Number Of Elements Input Field") {
numberOfElementsInputField = trans.GetComponent<InputField> ();
}
}
}
I have tried using transform instead of RectTransform or creating an array of InputFields:
InputField[] fields = GetComponentsInChildren();
and then iterating through that array, also.
Whatever solution I have tried, from the ones I found on the internet, I always get an Object reference not set to an instance of an object error when trying to use numberOfElementsInputField. It is not being assigned. In fact, putting a Debug.Log to get the length of the array, I get a zero length, as if no such components were found among the children objects. What am I doing wrong here?
I have also tried:
public GameObject numberOfElementsObject;
InputField numberOfElementsInputField;
...
void StartInputFields () {
numberOfElementsInputField = numberOfElementsObject.GetComponent<InputField>();
}
Dragging the Number Of Elements Input Field into the inspector numberOfElementsObject field, but get the same error.
How can I get a reference to the Input Field (Number Of Elements Input Field) from the script attached to its parent (Edition Panel) in order to control its input limits, displayed text, etc?
This was still waiting moderation when, after some hours of work, I found a way to do it. I'll describe it here to help people with the same problem and to allow those with better solutions to jump in.
Reproducing the hierarchy:
equipmentEditionScreen > Edition Panel > Parameters Scroll View > Content > Parameters Scroll View Content > Basic Properties Label > Number Of Elements Input Field.
First of all, I found out that GetComponentsInChildren returns null when called from a child of the instantiated prefab root (in this case, "Edition Panel" is the child to which I set my script). It works well when called from the parent node ("equipmentEditionScreen" in my example). Since the script is a component of the "Edition Panel" child, I had to find its parent. I did it through FindGameObjectWithTag, after setting a tag for the parent in the Inspector. But FindGameObjectWithTag only works on active objects. To check from a script on the child object, when its parent is activated, I've set the following code in the child ("Edition Panel") Update method:
GameObject parent;
bool initialized = false;
void Update(){
if (!initialized) {
parent = GameObject.FindGameObjectWithTag ("Equipment Edition Screen");
if (parent != null) {
StartInputFields ();
initialized = true;
}
}
}
So the StartInputFields method runs only when the parent is active (and only once).
Then I've set the StartInputFields method as follows:
void StartInputFields () {
InputField[] inputFields = parent.GetComponentsInChildren<InputField> ();
foreach (InputField input in inputFields) {
if (input.name == "Number Of Elements Input") {
numberOfElementsInputField = input;
}
}
}
From here on, I can control the input field by its text component "numberOfElementsInputField.text"
I would be better off by setting a public GameObject variable in "Edition Panel" and just dragging in its child "Number Of Elements Input Field" into the Inspector slot, but it doesn't seem to work. As I have been able to understand from some other threads, I would have to make the input field into a prefab and pull it from assets in order for it to work. Yet, if someone has a more efficient way of doing it, please tell.