Qué son los COMPONENTES en Unity y para qué se utilizan
Una COMPONENTE en Unity es un conjunto de datos y funciones que definen un comportamiento específico. Las componentes se asignan a los elementos de la escena llamados “GameObjects” y dotan a ese objeto de un comportamiento particular. En este artículo voy a compartir todo lo que sé acerca de las componentes en Unity que considero importante para poder mejorar tu manejo del motor Unity. Empecemos con una de las cosas más importantes:
En general, cualquier cosa que queramos hacer en Unity lo vamos a lograr a través de componentes asignadas a GameObjects.
Por ejemplo si queremos hacer que un objeto sea afectado por la gravedad, si queremos poder controlar el objeto con un mando o los inputs del teclado, si queremos reproducir sonidos, si queremos mostrar imágenes en pantalla. Todo esto y más se puede lograr utilizando distintas componentes asignadas a GameObjects de la escena en Unity.
Las componentes predefinidas en Unity
El motor Unity trae definidas por defecto una amplia variedad de componentes que logran distintos comportamientos, podemos verlas al seleccionar un GameObject de la jerarquía y en el inspector hacer clic en el botón “Add Component“, que se observa en la figura 1, allí tendremos todas las componentes disponibles ordenadas en distintas secciones dependiendo de la tarea que hagan.
Algunos ejemplos de estas componentes predefinidas son las componentes de tipo AudioSource que se encargan de reproducir sonidos, las componentes SpriteRenderer permiten mostrar sprites (imágenes) en pantalla, una componente MeshRenderer puede mostrar un modelo 3D en pantalla y una componente AnimatorController puede controlar un conjunto de animaciones y las distintas transiciones entre ellas.
Cómo crear nuevas componentes en Unity
Las componentes en Unity no son otra cosa que scripts de programación, en el caso de las componentes que vienen definidas por defecto en Unity se trata de scripts que no se pueden modificar, pero la clave en todo esto es que NOSOTROS PODEMOS CREAR NUEVOS SCRIPTS y al hacerlo ESTAMOS CREANDO NUEVAS COMPONENTES EN UNITY, estos scripts se pueden asignar a los GameObjects, exactamente igual que las componentes que vienen por definidas por defecto.
Al asignar un Script a un GameObject, un Script que no es otra cosa que una componente personalizada por nosotros, Unity ejecutará este Script, ejecutará sus instrucciones, lo que nos permitirá lograr cualquier cosa que queramos.
Para que Unity evalúe un script o una componente deben darse algunas condiciones que veremos a continuación.
Cómo hacer que una componente funcione en Unity
Para que una componente cualquiera haga su trabajo en Unity es necesario que se cumplan cuatro condiciones, a continuación vamos a listarlas y luego expandiremos la información sobre cada condición.
- La escena que está cargada durante la ejecución es la que contiene la componente.
- La componente debe existir en la escena.
- La componente debe encontrarse ACTIVA.
- La componente debe estar asignada a un GameObject activo de la escena
Si se cumplen estas cuatro condiciones la componente hará la tarea que tiene programada.
Hay que tener en cuenta que en algunos casos la componente podría parecer que no está haciendo su trabajo, tomemos el caso de un AudioSource que reproduce un sonido, podría haber momentos en los que el sonido no se reproduce, pero esto no significa que la componente no esté funcionando, si se cumplen las cuatro condiciones mencionadas anteriormente Unity está evaluando su comportamiento, solo que su comportamiento en ese momento quizás es no reproducir el sonido hasta que se dé la orden.
Condición 1: La escena donde se encuentra la componente debe estar cargada
Una aplicación hecha en Unity puede estar dividida en distintas escenas y cada escena tiene definido sus propios elementos. Al iniciar una aplicación en Unity se cargará automáticamente la escena que se haya definido con el índice 0 en la configuración de Build Settings de Unity y además en todo momento podemos pasar de una escena a la otra, por ejemplo al darle a un botón “Jugar” del menú principal podemos cargar otra escena donde está montado el juego.
Las componentes en Unity se asignan a los GameObjects y los GameObjects pertenecen a una escena en particular, por lo tanto si la componente que nos interesa se encuentra en una escena que no está cargada en un determinado momento, entonces su comportamiento no se estará ejecutando, simplemente porque esa componente no existe en ese preciso momento.
Condición 2: La componente debe existir en la escena
Para que una componente ejecute su comportamiento debe existir en la escena, esto significa que tenemos que “instanciarla”, crear una instancia de la componente que queremos utilizar. La forma más simple de hacer esto es elegir un GameObject apropiado (o crear uno) y luego en el inspector, con el botón “Add Component”, agregar la componente que queremos usar.
Este procedimiento para agregar una componente también puede hacerse a través de código, es decir desde un script podemos crear una instancia de una componente y asignarla a cualquier GameObject que queramos, para esto último necesitamos contar con la referencia del GameObject al que queremos asignarle la componente.
Si la componente que nos interesa no está instanciada, Unity no va a evaluar su comportamiento.
Condición 3: La componente debe encontrarse activa en la escena
En general las componentes en Unity, salvo algunas excepciones, tienen una casilla de habilitación que nos permite determinar si la componente se encuentra activa o inactiva, esto lo podemos ver en el inspector al seleccionar un GameObject, en la esquina superior izquierda de cada componente se encuentra esa casilla de habilitación, si está marcada la componente se encuentra activa, si está desmarcada la componente se encuentra inactiva.
Hay que tener en cuenta que el estado de activación puede modificarse a través de código, es decir dentro de un Script, si tenemos la referencia de ese componente, podemos activarlo o desactivarlo cuando lo necesitemos. Aquí tengo un vídeo en el que muestro cómo hacerlo.
Nota: La casilla de activación de un Script que hayamos creado no estará presente en el inspector si en el script no tenemos definida ninguna de las funciones internas de Unity (Awake, Start, Update, …). Tener en cuenta que estoy en la versión de Unity 2021.3.18f1, no estoy seguro si esto se cumple para versiones anteriores y no estoy seguro, aunque es probable, que si se cumpla para versiones posteriores.
Lee esto si tienes conocimientos de programación orientada a objetos
Las componentes en Unity pertenecen a la clase Component, en la jerarquía de clases existen clases como Behaviour o Renderer que heredan directamente de la clase Component, en este tipo de componentes la casilla de habilitación que vemos en el inspector muestra el estado de una variable interna llamada “enabled”, una variable que se encuentra definida en los Scripts que heredan su comportamiento de clases como Behaviour o Renderer.
Tomemos el caso de los objetos Behaviour, estos objetos son componentes pero no todos los componentes son Behaviours, por ejemplo un componente AudioSource es un Behaviour y por lo tanto tiene su casilla de habilitación. Pero hay otros componentes como Transform o Rigidbody que heredan directamente de Component y por esa razón no vemos la casilla de habilitación en el inspector.
Condición 4: La componente debe estar asignada a un GameObject activo en la escena
Los GameObjects de la jerarquía pueden encontrarse activos o inactivos en la escena. Podemos cambiar el estado de un GameObject seleccionándolo y en el inspector, utilizar la casilla que se encuentra arriba del todo a la izquierda, si esa casilla está marcada el GameObject está activo en la escena mientras que si está desmarcada el GameObject está inactivo en la escena. También es posible activar y desactivar un GameObject a través de código.
Si un GameObject se encuentra activo en la escena, Unity ejecutará automáticamente algunas funciones pertenecientes a las componentes activas que estén asignadas a ese GameObject, las funciones más conocidas pueden ser la función Awake, Start, Update y FixedUpdate, pero hay muchas otras funciones que forman parte del ciclo de inicialización y actualización de Unity.
Si el GameObject no se encuentra activo no se ejecutarán automáticamente estas funciones sobre las componentes que tenga asignadas el GameObject, sin embargo esto no quiere decir que no podamos usar esas componentes, por más que una componente esté inactiva, podríamos accederla y leer algun parámetro que nos interese.
En Unity se puede establecer una jerarquía entre distintos GameObjects, es decir un GameObject puede actuar como padre de otros GameObject, es decir puede ser un parent, mientras que los GameObjects hijo serían sus childs. Los childs de un GameObject se verán afectados por algunas cosas que le ocurran a sus parents, por ejemplo si trasladamos el objeto parent, todos sus childs se moverán en conjunto. Este comportamiento también ocurre con el estado de activación del GameObject, si el parent se desactiva, todos sus childs (y los childs de sus childs) se desactivarán también. Por esta razón, para que una componente funcione en Unity, no solo el GameObject al que está asignada tiene que estar activo, sino todos los GameObjects que se encuentren jerarquía arriba.