Diseño y desarrollo de videojuegos con Unity Introducción a Unity 3D Quedan rigurosamente prohibidas, sin la autorización escrita de los titulares del Copyright, bajo las sanciones establecidas en las leyes, la reproducción total o parcial de esta obra por cualquier medio o procedimiento, comprendidos la reprografía y el tratamiento informático, y la distribución de ejemplares de ella mediante alquiler o préstamo públicos. Diríjase a CEDRO (Centro Español de Derechos Reprográficos, www.cedro.org) si necesita fotocopiar o escanear algún fragmento de esta obra. INICIATIVA Y COORDINACIÓN DEUSTO FORMACIÓN COLABORADORES Realización: Oneclick Diseño y Software, S. L. Elaboración de contenidos: Iván Cerezo Vivas Maestro, formador de videojuegos y desarrollador. Jefe de estudios y formador de los cursos de programación con Unity 3D en AulaArcade. Revisión contenidos: INICIATIVA Y COORDINACIÓN Jordi Mula Ferrer DEUSTO FORMACIÓN Desarrollador y diseñador de videojuegos. Profesor de desarrollo y diseño de videojuegos. COLABORADORES Cofundador de Arcadio Lab. Realización: Oneclick Diseño y Software, S. L. Supervisión técnica y pedagógica: Departamento de Enseñanza de Deusto Formación Elaboración de contenidos: Iván Cerezo Vivas Coordinación editorial: Maestro, formador de videojuegos y desarrollador. Departamento Producto de Formación Jefe de estudiosde y formador de Deusto los cursos de programación con Unity 3D en AulaArcade. © Planeta DeAgostini Formación, S. L. U. Barcelona (España), 2021 Revisión contenidos: Jordi Mula Ferrer Primera edición: enero 2021. Desarrollador y diseñador de videojuegos. Profesor de desarrollo y diseño de videojuegos. ISBN: 978-84-1300-556-0 (Obra completa) Cofundador de Arcadio Lab. ISBN: 978-84-1300-559-1 (Introducción a Unity) Supervisión técnica y pedagógica: Depósito legal:de B 19983-2020 Departamento Enseñanza de Deusto Formación Impreso por: editorial: Coordinación SERVINFORM de Producto de Deusto Formación Departamento Avenida de los Premios Nobel, 37 Polígono © PlanetaCasablanca DeAgostini Formación, S. L. U. 28850 Torrejón de Ardoz Barcelona (España), 2021 (Madrid) Printed in Spain ISBN: 978-84-1300-556-0 (Obra completa) Impreso en España ISBN: 978-84-1300-559-1 (Introducción a Unity) Esquema de contenido 1. Integrated development environment (IDE) 1.1. Instalación de Unity 1.2. Creación de un proyecto 1.3. Modo juego 1.4. Ventanas 1.4.1. Scene 1.4.2. Hierarchy 1.4.3. Inspector 1.4.4. Project 1.4.5. Console 1.4.6. Project 1.5. Layers 1.6. Tags 1.7. Assets 2. Componentes 2.1. Transform 2.1.1. Propiedades 2.1.2. Métodos 2.2. Camera 2.3. Creación de componentes 2.3.1. Lenguajes de programación 2.3.2. C# 2.3.3. Editor de código 2.3.4. Programación en Unity 2.3.5. Comunicación entre clases 2.3.6. Uso de los componentes desde Unity 3. Escenas 3.1. Gestión y uso de las escenas Resumen Glosario Introducción En esta unidad didáctica vamos a ayudarte a dar los primeros pasos para crear tus propios juegos. En primer lugar, haremos un recorrido por Unity 3D y veremos qué necesitas para adquirirlo y para empezar a utilizarlo. Después veremos cómo se organiza la herramienta y cuáles son los conceptos más importantes que hay que tener en cuenta a la hora de trabajar en Unity 3D. Por último, aprenderemos cómo dotar de comportamiento a los objetos y crearemos nuestros primeros objetos interactivos. Una vez terminado este módulo sabrás crear y gestionar escenas. Además, al final hay un glosario donde encontrarás los conceptos más complejos e importantes de este módulo. Introducción 5 1. Integrated development environment (IDE) Un integrated development environment (entorno de desarrollo integrado; en adelante, IDE) es, como su propio nombre deja entrever, un software que reúne las herramientas necesarias para desarrollar programas, aplicaciones o, en el caso de Unity 3D, juegos. Estos programas permiten al desarrollador tener acceso a distintas tareas del desarrollo de manera sencilla: edición de código fuente, construcción del programa y debuggeo o depuración de fallos. Por lo tanto, cuantas más posibilidades nos brinde un IDE, más fácil será nuestra tarea de desarrollo. Podemos encontrar IDE sencillos para crear programas de consola o de ventana (como Eclipse o NetBeans) y los llamados Game IDE o game environment (como Unity 3D, Unreal Engine, RPG Maker o Godot), que son los que mejor se adaptan a nuestra tarea y, por tanto, los que más la facilitarán. De entre la gran oferta de Game IDE que existen vamos a enseñarte a utilizar Unity 3D (en adelante, Unity o el editor) por diversos motivos, la mayoría centrados en las facilidades que nos brinda. Desde su página web tenemos acceso a Scripting Reference (referencias de código), a Unity Manual y a tutoriales específicos que los desarrolladores del IDE comparten de forma gratuita. Además, Unity cuenta con unos recursos estándares de los que hablare- ! mos más adelante. También accederemos a la Asset Store, la tienda de Unity, donde hay gran cantidad de materiales, tanto gratuitos como de pago. Recuerda Otro factor determinante por el que se ha elegido este programa es su En las plataformas plasticidad o flexibilidad. En el editor se puede modificar la interfaz móviles no tenemos para adaptarla a nuestras necesidades, así como crear ventanas o modi- acceso a teclados o ficar las ya existentes. controladores con la misma facilidad que Uno de los mayores puntos fuertes de Unity es su orientación multipla- con otras plataformas, taforma: permite desarrollar un mismo juego para distintas plataformas las cuales es difícil (móvil, PC, Mac…) con solo modificar algunas opciones y, por supuesto, que tengan pantallas adaptar las entradas de información del jugador. Integrated development environment (IDE) táctiles. 7 1.1. Instalación de Unity Para instalar el editor de Unity, el primer paso que has de realizar es dirigirte a la web del IDE http: store.unity.com. Allí podrás elegir el plan que mejor se amolde a tus necesidades: ! • Personal (gratuito). Permite utilizar todas las opciones del editor, pero limita la cantidad de ingresos que podemos generar con nuestros jue- Recuerda gos a cien mil dólares (100.000 $). Los planes de pago están pensados para • Student (gratuito). Sus características son parecidas a la versión perso- profesionales, pero nal, pero además permite trabajar en equipo, con más miembros. Para no es necesario pagar poder usar esta versión hay que poder acreditar ser estudiante de un centro educativo. para usar Unity3D. • Plus (de pago). Ofrece descuentos en la tienda de recursos, un límite de ingresos mayor y algunas funcionalidades externas. • Pro (de pago). No tiene límite de ingresos e incluye una mejora de las funcionalidades externas, mayores descuentos y acceso al código fuente del programa. • Enterprise (de pago). Ofrece todas las funcionalidades. A continuación, elige el plan Personal pulsando en el botón Get Started y descarga la última versión del programa a través de la opción Start Here y aceptando los términos de servicio. Una vez descargado, ejecuta el instalador de Unity Hub. Este programa gestiona el inicio de Unity y te permite trabajar con diferentes ! versiones de Unity. Dentro de Unity Hub, lo primero que hay que hacer es acceder a la cuenta de Unity clicando en el icono de usuario, arriba a la derecha: Recuerda Gracias a Unity Hub podrás acceder a los últimos proyectos Puedes acceder a través de una cuenta de Google o Facebook o a través en los que hayas de una cuenta de correo. trabajado, instalar diferentes versiones de Unity o acceder a recursos de aprendizaje. 8 Introducción a Unity 3D Una vez hayas accedido a la cuenta puedes generar una licencia de tipo personal. Para ello, debes dirigirte a la rueda de la barra de herramientas y acceder a las preferencias de Unity Hub. Allí has de elegir la opción de License Management y, una vez dentro, clicar sobre Activate New License. En nuestro caso crearemos una licencia de tipo Personal, eligiendo cualquiera de las dos opciones personales que nos ofrece el programa. Por último, has de volver atrás para salir de las preferencias de Unity Hub ! y acceder al menú Installs, donde podrás añadir una nueva instalación de Unity haciendo clic en Add. Desde aquí podrás instalar las últimas versiones del motor gráfico. Cuando veas una versión etiquetada como LTS, debes tener en cuenta que es una versión a la que se le dará sopor- Recuerda te y parches durante un largo periodo de existencia. Una vez selecciona- No pasa nada si no da la versión de Unity a instalar, podrás seleccionar qué módulos quieres instalas todos los instalar. Los módulos se módulos al principio. pueden añadir siempre Siempre podrás volver que quieras a una insta- al menú de Installs lación existente hacien- y seleccionar los do clic en los tres puntos componentes que que acompañan al nom- necesites para cada bre de la instalación. instalación. Integrated development environment (IDE) 9 1.2. Creación de un proyecto ! Unity se organiza por proyectos. Un proyecto es un conjunto de recursos Recuerda necesarios para el programa y que se utilizan para crear un juego. Si no trabajas en tu propio equipo, cierra Al crear un proyecto se establece un orden de carpetas. Son las siguientes: siempre la sesión para evitar que el programa recuerde • Assets. Se crea vacía y su cometido es albergar todos los recursos y carpetas que se necesitarán en el proyecto. Será la única carpeta sobre tus datos. la que trabajarás directamente. • Library. Aquí está todo lo que Unity 3D necesita internamente para funcionar. • Project Settings. Contiene todos los archivos que hacen referencia a las distintas configuraciones del programa (gráficos, leyes de física, etc.) y que modificaremos siempre desde el menú del editor: Edit → Project Settings. Una vez has configurado el programa y sabes qué es un proyecto, es hora de crear uno. Al iniciar Unity Hub tendrás la posibilidad de abrir los últimos proyectos(1), añadir un proyecto existente desde una carpeta(2) o crear un nuevo proyecto(3). Al elegir la opción New, accederás a la ventana de nuevo proyecto. En ella tendrás que indicar el nombre del proyecto y dónde quieres guardarlo. También tendrás que indicar si el juego que vas a desarrollar será en 2D o en 3D, o si quieres usar alguno de los nuevos sistemas de Render Pipeline para que el editor pueda autoconfigurarse y facilitarte el trabajo. Por último, podrás decidir si quieres añadir algún paquete de recursos para que tu proyecto arranque con ellos. 10 Introducción a Unity 3D + 1.3. Modo juego Una vez que hayas abierto o creado un proyecto podrás hacer que el editor se ejecute en modo juego. Para ello basta con pulsar Play, que es Consejo el primer botón que aparece en la parte superior central del editor. Al Puedes cambiar el pulsarlo, el editor cambiará de color y, si tenemos una escena funcional, color que adquiere el podremos jugar a nuestro juego. editor en modo juego siguiendo esta ruta: También podemos pausar el curso del juego utilizando el siguiente bo- Edit → Preferences → tón, Pause, y avanzar imagen a imagen (o frame) pulsando el tercero, Colors → Playmode Step, pero solo saldremos del modo juego si volvemos a pulsar Play. tint. Las modificaciones que hagas de los distintos objetos de juego no se guardarán si las haces estando en modo juego, por lo que es crucial que sepas en todo momento si lo estás usando o no. Sin embargo, las modificaciones que hagas de los recursos sí serán efectivas. 1.4. Ventanas Como ya dijimos, Unity 3D está dotado de gran plasticidad, y esto es, en parte, gracias a su estructura de ventanas. Con ellas tendremos acceso a distintos aspectos del desarrollo del videojuego contemplados por el equipo de desarrollo de Unity; pero, en caso de que necesitemos acceso + a algo que no está incluido, tendremos la oportunidad de crear nuestra propia ventana, aunque esto, no obstante, requiere un nivel avanzado de conocimientos del programa. Consejo Puedes ver todas las ventanas de Unity en Cada ventana del editor incluye opciones específicas. Además, tenemos el menú desplegable la posibilidad de redimensionarlas y posicionarlas como nos resulte más Window del editor. cómodo, así como de acumular más de una ventana en un sistema de pestañas mediante el solapamiento con la última seleccionada. Para mover una ventana basta con hacer clic en el nombre y arrastrarla hacia el lugar que queramos. Si coincide con otra, se solaparán; si cae en un hueco donde cabe la ventana, se colocará en su lugar, y, en caso contrario, se quedará como una ventana flotante. De esta forma, crearemos nuestra propia configuración o layout de ventanas. Integrated development environment (IDE) 11 Unity 3D presenta hasta cinco configuraciones por defecto que incluyen las ventanas principales. Se encuentran en la esquina superior derecha de la interfaz del programa y pueden ampliarse o modificarse si es necesario. Puesto que la configuración debe responder a tus necesidades y facilitarte el trabajo, es posible crear una propia. Para ello, simplemente tienes que colocar las ventanas que quieras en la disposición que más te guste, desplegar el menú Layout y pulsar Save Layout… para guardarla. Para elegir la configuración que mejor se adapte a tus necesidades es esencial aprender qué utilidad tienen las ventanas más importantes. 1.4.1. Scene Como su propio nombre indica, esta ventana nos muestra la configuración de la escena. Pero ¿qué es una escena? Se puede decir que una escena es la organización espacial de un conjunto de objetos con sus propiedades específicas. En muchas ocasiones, una escena coincide directamente con el nivel del juego, y en ella incluiremos todo lo necesario para que el jugador desarrolle su actividad. Ahora que sabes qué es una escena, podrás deducir que el fin de la ventana que nos ocupa es navegar por la escena para colocar, configurar o revisar los objetos que la componen. Como cada ventana, Scene tiene una serie de opciones específicas, que explicamos a continuación (de izquierda a derecha en la imagen): 12 Introducción a Unity 3D • Desplegable Shaded. Nos brinda un conjunto de opciones que modifican la vista que tenemos para hacer hincapié en distintos aspectos gráficos: los materiales (Shaded), los polígonos (Wireframe), etc. • Toggle 2D. Cuando está activado, elimina la profundidad de la escena para que podamos trabajar más fácilmente en 2D. • Toggle de iluminación. Cuando está activado, muestra el efecto que tienen las luces sobre los objetos de la escena. • Toggle de sonido. Cuando está activado, podemos escuchar todos los sonidos que forman parte de la escena sin necesidad de entrar en el modo juego. • Desplegable de imagen. Se trata de un conjunto de toggles que nos mostrarán u ocultarán distintos aspectos gráficos de la escena (fondo, niebla, destellos, materiales animados o efectos de imágenes). • Gizmos. Se trata de una imagen representativa de un comportamiento, como el de una luz, la cámara o un recurso de audio. Este menú desplegable nos permitirá mostrar u ocultar algunos gizmos concretos o todos, según lo creamos conveniente. • Buscar. En este cuadro de búsqueda podemos introducir el nombre de un objeto cualquiera para localizarlo en la escena. Por último, con el gizmo de ejes que aparece en la parte superior derecha que aparece en Scene podemos modificar el tipo de perspectiva con el que miramos a nuestra escena y la dirección en la que lo hacemos. Para cambiar de perspectiva entre normal y ortográfica debemos hacer clic en el cubo al que apuntan los ejes (los conos), y si lo que queremos es mirar desde un eje en concreto bastará con pulsar sobre él. Podrás comprobar que, además de estas opciones específicas, cada una de las ventanas muestra un pequeño menú desplegable en la parte superior derecha. En el caso de la ventana Scene, este menú nos permite minimizarla o maximizarla. El editor cuenta también con opciones específicas para nuestro manejo de objetos en Scene —las herramientas—, además del toggle de posición y el de posición relativa. Integrated development environment (IDE) 13 Herramientas Existen cinco herramientas, situadas en la parte superior izquierda del editor, y cada una de ellas hará que nuestra interacción con la ventana Scene varíe. Esas cinco herramientas son, de izquierda a derecha, mano, posición, rotación, escala y rectángulo. La primera nos permitirá movernos por la escena haciendo clic y arrastrando. Las tres siguientes nos ayudarán a mover, girar o cambiar el tamaño de los objetos de la escena una vez que los hayamos seleccionado. La última nos permitirá hacer lo mismo que estas tres, pero cuando estemos trabajando con objetos 2D. Toggle de posición En las últimas cuatro herramientas el gizmo que les corresponde se situará en el pivote o centro del objeto en función de lo que indique este toggle, lo que hará que el movimiento, la rotación o la escala que se aplique a ese objeto se haga desde ese punto interno del objeto. Toggle de posición relativa De igual forma, al aplicar cualquiera de esas transformaciones, habrá que tener en cuenta si queremos aplicarlas en relación con los valores propios del objeto o con los globales de la escena; es decir, si un objeto está girado 90° a la derecha, podremos moverlo hacia delante con respecto de la escena, que se mantiene constante, o hacia delante con respecto del propio objeto, cuya orientación ya no coincidirá con la escena, lo que producirá un movimiento hacia la derecha si tenemos en cuenta la orientación de la escena. Este toggle nos permitirá elegir en todo momento si la transformación que hagamos se aplicará en relación con los valores locales o con los valores globales. 1.4.2. Hierarchy La ventana de Hierarchy, que hace referencia a la jerarquía, nos muestra una lista con todos los objetos que forman parte de una escena. A cada uno de ellos lo llamaremos GameObject. 14 Introducción a Unity 3D En este caso, las opciones de las que disponemos son más reducidas, pero tan importantes o más, ya que desde Hierarchy podemos crear distintos tipos de GameObjects para nuestra escena desplegando el menú Create o haciendo clic con el botón derecho y seleccionando cualquier tipo de objeto. Otro aspecto importante de esta ventana es que nos muestra las relaciones de parentesco entre los objetos a la vez que nos permite crear otras nuevas arrastrando el nombre de un GameObject sobre otro en la lista. Así, el objeto que hemos arrastrado será «hijo» del objeto sobre el que lo hemos soltado. La ventana de jerarquía nos permite introducir en ella más de una escena a la vez para poder configurarlas con coherencia espacial, estética, etc. De alguna manera, podríamos ver una escena como el objeto padre de todos los GameObjects que contiene, sin olvidar que una escena no es un GameObject. Comprobarás que cada escena tiene, además, algunas opciones propias que nos facilitan el guardado, la carga o la recuperación de la última configuración guardada de una escena. Cabe resaltar el papel de la ordenación en Hierarchy, ya que aquella ! será también la ruta que siga el programa para cargar cada uno de los GameObjects, de forma que, cuanto más arriba aparezcan, antes se cargarán. Recuerda Hay una pequeña excepción que nos permite ordenar los objetos de El orden alfanumérico la escena siguiendo un criterio alfanumérico, es decir, en función del respeta las relaciones nombre que tienen asignado. Está junto al cuadro de búsqueda y se pue- de parentesco de los de elegir el tipo de orden con un solo clic. Para activar esta opción, abre GameObjects. el menú Edit y selecciona la opción Preferences para acceder a las preferencias del editor. Una vez ahí, busca y activa la opción Enable Alpha Numeric Sorting (habilitar el orden alfanumérico) en General. 1.4.3. Inspector La ventana Inspector nos da información sobre el objeto que está seleccionado en cada momento, ya sea un GameObject (forma parte de la escena) o un recurso, con algunas excepciones, como las preferencias de usuario necesarias para construir la versión final del juego. Integrated development environment (IDE) 15 Si seleccionas un GameObject, esta ventana mostrará sus características, propiedades o comportamientos, atributos estos que se adjuntan al objeto mediante los componentes, en los que repararemos más adelante. Por norma general, Inspector será nuestra herramienta para configurar cada uno de los GameObjects o para modificar las características de algunos recursos, por lo que su utilidad es muy general. De hecho, si seleccionamos un archivo de audio que forma parte de nuestro proyecto, veremos información relativa al sonido, y, si es una imagen, a la información sobre ella. Así, se puede deducir que el inspector será completamente distinto en función del tipo de recurso. No obstante, siempre podremos utilizar el botón Open que aparecerá junto al nombre del recurso para abrirlo en nuestro sistema operativo. En cualquier caso, las únicas opciones permanentes de Inspector están en el pequeño menú desplegable que tiene cada ventana. Además de cerrar la ventana, añadir otra o maximizarla (como en todas las demás), podremos elegir el modo de visualización: Normal, que muestra las características que se permiten desde código, o Debug, que muestra también parámetros en principio escondidos. Otra opción específica es Lock (bloquear), con la que podemos mantener la información de un objeto en el inspector mientras seleccionamos otros. El pequeño candado situado junto al desplegable te indicará si el inspector está o no bloqueado. Por último, fíjate en que al seleccionar un recurso cualquiera aparecerá un pequeño libro con una interrogación, generalmente junto al nombre del recurso —depende del recurso en cuestión—. Este pequeño libro te llevará a la ayuda de Unity (el manual), donde podrás encontrar todos sus aspectos representativos. 16 Introducción a Unity 3D 1.4.4. Project En la ventana que nos ocupa vamos a encontrar todos los recursos que introduzcamos en la carpeta Assets de nuestro proyecto. De hecho, para encontrar cualquier archivo o carpeta en nuestro sistema operativo, bastará con hacer clic con el botón derecho del ratón sobre uno de ellos y seleccionar Show in Explorer/Finder. ! Para agregar nuevos recursos tenemos varias opciones: Recuerda • crearlos desde el editor, La carpeta Assets contiene todos los • introducirlos de forma manual, recursos y carpetas que necesitamos para • descargarlos de la tienda. nuestro proyecto. En cualquiera de los tres casos, podremos seleccionarlos desde esta ventana para ver sus características en la ventana Inspector. Podemos crear estos recursos desde la propia ventana Project, donde encontrarás el menú desplegable Create, con gran cantidad de opciones que van desde crear una carpeta hasta crear materiales físicos o visuales, archivos de código, escenas, etc. Estas mismas opciones las podrás encontrar haciendo clic con el botón derecho o desplegando el menú Assets en la ventana de Unity y seleccionando el desplegable Create. Igual que en Hierarchy y Scene, Project tiene un cuadro de búsqueda que, en este caso, no busca por la escena en la que estamos trabajando, sino en todo el proyecto, y tiene algunas opciones de búsqueda extras para facilitarnos la tarea, ya que, por norma general, Project estará cada vez más lleno de recursos y su acceso se nos irá dificultando. Estos extras son la búsqueda por tipo de recurso, que podremos elegir pulsando el botón que se encuentra junto a la barra de búsqueda, o por etiquetas. Integrated development environment (IDE) 17 Por último, podemos guardar cualquier búsqueda que realicemos pulsando en el último botón de esta fila, de manera que la añadiremos a Favorites y podremos acceder a ella siempre que queramos. Si recuerdas las opciones de las ventanas anteriores, hemos reparado siempre en el menú desplegable de cada una de ellas. En este caso, podemos encontrar una opción extra: elegir el modo en que queremos visualizar el inspector. ¿Una columna o dos? La segunda es la opción por defecto y muestra la ventana dividida en dos partes: a la izquierda, las carpetas del proyecto, y a la derecha, el contenido de la carpeta que tengamos seleccionada en ese momento. Si decidimos trabajar con una columna, veremos todas las carpetas con un indicador para desplegar u ocultar su contenido —si hay—, el cual veremos del mismo modo que las carpetas. Debes saber que Unity tiene reservados algunos nombres de carpetas para unas funciones concretas, por lo que podrás nombrarlas como quieras siempre que no utilices ninguno de ellos. Estos son algunos ejemplos: • Standard Assets. Será la primera carpeta que tendrá en cuenta Unity a la hora de construir tu juego y de convertirlo en una aplicación ejecutable. • Editor. Esta carpeta no se incluirá en la construcción del ejecutable y está pensada para el código que modifique el editor en general. • Resources. Podemos acceder al contenido de esta carpeta desde código para utilizar los recursos que contiene. Si la llenas demasiado, el proyecto pesará mucho. • Gizmos. Si queremos que alguno de los comportamientos que creemos tenga un gizmo, tendremos que añadir la imagen en esta carpeta. El resto de opciones de esta ventana están relacionadas directamente con los recursos, así que repararemos en ellas más adelante. 18 Introducción a Unity 3D + 1.4.5. Console La consola es el método que tiene el programa para comunicarse con nosotros. Desde ella tendremos acceso a los errores que haya en el có- Recursos digo o a los mensajes que le pidamos que nos muestre. Por lo tanto, la Puedes encontrar consola es nuestra principal fuente de información para saber si hay el resto de carpetas problemas con nuestro código. La utilizaremos cuando creemos nues- especiales en la tro primer componente en la siguiente parte de la unidad. documentación de Unity. Las opciones propias de la consola cuentan con el botón Clear, que elimina todos los mensajes que esta contenga, además de varios toggles: • Collapse. Si está activado, mostrará juntos todos los mensajes iguales, esto es, con el mismo texto pero también con la misma procedencia. • Clear on Play. Si está activado, limpiará la consola cuando ejecutemos el modo juego en el editor. • Error Pause. Esta opción obligará al editor a pausar el modo juego si la consola registra algún error. • Mensajes, Advertencias y Errores. Estas opciones representan los tres tipos de mensaje que podemos enviar o recibir en la consola y nos permiten mostrar u ocultar cualquiera de ellos. 1.4.6. Project En la ventana Game veremos la perspectiva final del juego, la que tendrá el jugador. Observa que en esta ventana no podemos seleccionar ningún objeto, solo vemos una imagen de lo que registra la cámara que tenemos en la escena. En caso de que tengamos más de una cámara, Unity superpondrá cada una de las imágenes y veremos la que se encuentre primero en la «pila» de imágenes. Integrated development environment (IDE) 19 El tamaño dependerá directamente de la resolución de pantalla que ! indiquemos en esta ventana. En el segundo desplegable de sus opciones podremos elegir la resolución o una relación de aspecto o aspect ratio. La resolución indicará cuántos píxeles miden el ancho y el alto Recuerda de la pantalla (por ejemplo, 1920 x 1080), mientras que la relación de El menú desplegable aspecto hace referencia a la proporción de tamaño entre la altura y la Gizmos nos permitirá anchura de aquella (por ejemplo, 4:3). mostrar u ocultar algunos gizmos Si quieres utilizar una resolución o una relación concretos o todos, de aspecto no contemplada en el editor, añáde- según lo creamos la pulsando en la última opción del desplega- conveniente. ble, asígnale un nombre y un tamaño, y utilízala siempre que quieras. Puede ocurrir que la resolución que hemos elegido sea tan grande que no quepa en la ventana Game. No te preocupes, porque en ese caso podremos modificar la escala de la imagen con la barra de ajuste Scale que aparece junto al menú anterior, de forma que podamos encajarla o aumentar alguna parte si queremos. En cualquier caso, Game también cuenta con un toggle para maximizar la ventana cuando entremos en el modo juego: Maximize On Play. El toggle Mute Audio silenciará todos los sonidos que se reproduzcan en la escena y Stats mostrará información sobre el rendimiento de la misma con respecto al audio, los gráficos o la conexión, en caso de que trabajemos en un proyecto online. Por último, con el menú desplegable Display podremos elegir sobre qué pantalla queremos ver la ventana Game. Esto es posible gracias a la opción multipantalla que nos ofrece Unity y que podremos configurar en las cámaras. 20 Introducción a Unity 3D 1.5. Layers Debes tener en mente que las ventanas están pensadas para interactuar constantemente y que solo así podrás sacar el máximo rendimiento al editor. Como verás, el uso de las capas o layers es un claro ejemplo de ello. Controlar el inspector te dará aún más facilidades a la hora de trabajar con la ventana Scene gracias al uso de las capas, que son conjuntos de GameObjects agrupados con distintos fines, por ejemplo, ocultarlos en la ventana de Scene para poder centrarnos en otros aspectos. Asignar una capa Para asignar una capa, seleccionamos el GameObject (haciendo clic sobre él) y desplegamos el menú Layer que aparece en la parte superior de la ventana Inspector. Ahí encontraremos distintas capas que Unity contempla por defecto y que podrían ser suficientes para nuestro proyecto. Si lo fueran, bastará con seleccionar una de las que ya existen y el objeto pertenecerá automáticamente a esa capa. Crear una capa En caso de que necesitemos capas nuevas, utilizaremos la opción Add Layer. Esta opción nos manda al gestor de etiquetas y capas, donde podremos añadir capas nuevas o gestionar las que ya hayamos añadido. Otra forma de acceder al gestor es la siguiente: Edit → Project Settings → Tags & Layers. Una vez ahí, bastará con que despliegues la lista que quieres editar —en este caso, Layers— y rellenes uno de los huecos vacíos para crear una capa. Asígnale un nombre lo más representativo posible para que cualquier compañero de proyecto, o tú mismo, pueda entenderla a la primera en el futuro. Ahora que tienes una capa nueva, vuelve a seleccionar el GameObject y asígnasela. Integrated development environment (IDE) 21 Usar las capas Como indicábamos, podemos usar las capas para esconder o hacer visibles distintos GameObjects. Una vez asignada la capa a cada uno de los objetos, el editor nos permitirá indicar qué capas queremos mostrar en la ventana Scene con el desplegable Layers de la parte superior derecha del editor. En dicho menú encontrarás los nombres de todas las capas de tu proyecto y, junto a cada uno, un ojo y un candado. El ojo es un toggle que indica la visibilidad de la capa. Si clicas sobre él, el ojo se cierra y la capa deja de mostrarse en la escena. El cambio, el candado bloquea la capa para evitar seleccionar por error objetos que no necesitamos —por ejemplo, los fondos de un escenario—, aunque esta restricción solo funciona en la ventana Scene; es decir, podrás seguir seleccionando los GameObjects desde Hierarchy. Por supuesto, si quieres desbloquear la capa, solo tendrás que volver a pulsar sobre el candado. Otro de los usos más importantes de las capas está relacionado con las físicas. Si seleccionas Edit → Project Settings → Physics en el menú del editor, podrás ver, abajo del todo del inspector, una matriz de capas en la que se indican cuáles pueden interactuar con cuáles con un toggle para cada relación directa. 1.6. Tags Otra forma de agrupar GameObjects son las etiquetas o tags. Se crean desde el mismo menú que las capas, pero en esta ocasión pulsaremos la tecla + para añadir una nueva; y se asignan en el menú desplegable de la parte superior izquierda del inspector mientras tenemos seleccionado el GameObject que queremos etiquetar. 22 Introducción a Unity 3D Las funciones de las etiquetas pasan por encontrar objetos de un mismo grupo desde código o identificarlos como tales. Por ejemplo, tendremos una etiqueta para todos los enemigos que nos indicará que pueden herir al jugador. De esta forma, cuando dos GameObjects interactúen comprobaremos sus etiquetas y les indicaremos que actúen en consecuencia. ! 1.7. Assets Si haces memoria, te darás cuenta de que el nombre de este apartado es el mismo que recibe nuestra carpeta principal del proyecto. En ella intro- Recuerda ducimos todos los recursos o assets que pretendemos usar en nuestro Puedes crear capas y etiquetas desde juego. Efectivamente, el nombre de la carpeta hace referencia a los recursos de Unity. Cada uno de los archivos que recopilemos en la ventana del proyecto será un recurso: un grupo de datos/variables, un modelo 3D, un archivo de texto o un GameObject. las opciones Add Layer o Add Tag, o directamente desde el gestor de capas y etiquetas: Edit → Project Settings → Tags & Layers. Si nos ceñimos a la definición de GameObject no podemos decir que sea realmente un recurso; de hecho, no lo es. Entonces ¿cómo podemos guardar un objeto específico de una escena concreta para reuti- ! lizarlo? Prefabs Recuerda La respuesta son los prefabs. Unity contempla un tipo de recurso llama- Un GameObject es, do prefab que está configurado para convertirse en un GameObject al básicamente, un incluirlo en una escena. contenedor de comportamientos que tiene un lugar en la escena. Para crear un prefab tenemos varias opciones. La primera es configurar un GameObject en una escena cualquiera y, una vez hecho, arrastrar el objeto desde la ventana Hierarchy hasta la ventana Project. Integrated development environment (IDE) 23 La otra opción es crear el prefab desde el menú desplegable de la ventana del proyecto. Una vez creado, si seleccionamos el prefab, el inspector mostrará el mismo aspecto que cuando tenemos seleccionado un GameObject. El uso de prefabs es altamente recomendable en objetos que vayan a reutilizarse a lo largo de todo el proyecto, porque nos da la posibilidad de aplicar cambios instantáneos a todas las copias del mismo. Estos cambios se pueden realizar desde el propio prefab o desde alguna copia, con la diferencia de que al realizarlos con una copia tendremos que confirmar su aplicación al resto usando el nuevo botón Apply que muestra el inspector en su parte superior. Para utilizar copias de este GameObject preconfigurado bastará con que lo arrastremos a la ventana de Scene (indicándole así su nueva posición) o a la de Hierarchy (indicándole así alguna relación de parentesco si lo soltamos sobre otro objeto). ! Tanto si importas paquetes de recursos o Unity Packages como si los exportas, verás una ventana emergente en la que tendrás que decidir qué recursos quieres introducir en el proyecto o en el paquete, respecti- Recuerda vamente. Puedes crear otros Otros recursos recursos en Unity mediante el menú Create de la ventana Por norma general, tendrás que añadir recursos de uno en uno y no en Project. paquetes de Unity. Para añadir estos recursos bastará con incluirlos en la carpeta Assets, ya sea arrastrándolos desde tu sistema operativo a la ventana Project o copiándolos en la propia carpeta desde el explorador de tu sistema. Asset Store A todas estas posibilidades de introducir recursos en nuestro proyecto hay que sumar las existentes en la Asset Store, donde podremos encontrar una gran cantidad de recursos gratuitos listos para usar: personajes, objetos 3D, código, imágenes, etc. 24 Introducción a Unity 3D Puedes acceder a la Asset Store desde: Window → Asset Store. Integrated development environment (IDE) 25 2. Componentes Hasta ahora hemos hablado de Unity y de sus recursos, pero habrás notado que en ningún momento hemos reparado en los comportamientos que forzosamente tendrán los GameObjects que utilicemos en nuestros proyectos. Cuando hablamos de comportamientos hacemos referencia a actividades que los objetos llevan a cabo, tareas muy dispares, entre las que se encuentran realizar un movimiento, mostrar una imagen o simular comportamientos físicos. Cada vez que queramos que un GameObject lleve a cabo un comportamiento, tendremos que indicárselo añadiéndole un componente. Para ello, debemos seleccionar el objeto al que queremos añadírselo, ya sea un GameObject o un prefab. Una vez seleccionado, veremos que la ventana de inspector muestra el botón Add Component. Pulsa este botón para ver todos los componentes que podemos añadir organizados por grupos desplegables. Estas mismas opciones de adición están disponibles en el menú del editor Component, en el que también podemos desplegar el menú anterior. Puedes encontrarte en la situación de querer añadir a un objeto un componente que ya estás utilizando en otro. Si es así, solo tienes que desplegar el menú del propio componente que quieres copiar y seleccionar Copy Component (copiar componente). Una vez hecho esto, despliega el menú de un componente cualquiera del objeto receptor y pulsa Paste Component As New (pegar componente como uno nuevo). Así no solo habrás añadido un componente, sino que, además, habrás copiado los valores del primero. Al añadir un componente, el editor nos muestra todas las opciones disponibles, que serán las que contempla el editor si estás trabajando en un proyecto vacío. Ya con estos, las opciones que nos da Unity 3D son bastantes. 26 Introducción a Unity 3D De entre ellas, los componentes que más debes tener en cuenta son los siguientes: • Transform. El único componente que debe tener todo GameObject. Nos indica la posición, la rotación y la escala del mismo. • Camera. Hace que un GameObject actúe como cámara, permitiéndonos ver en la ventana Game lo que está a su alcance. Como ya indicamos, las cámaras serán los ojos del jugador. • Light. Convierte el GameObject en un emisor de luz de distintos tipos. Siempre que crees una escena nueva encontrarás una luz de tipo direccional en ella. • Mesh Renderer, Sprite Renderer y Canvas Renderer. Son los responsables de que podamos ver los distintos GameObjects, ya sean objetos 2D, 3D o elementos de interfaz, respectivamente. • Colliders. Dota de límites físicos a los GameObjects, ya sea para que actúen como barrera para detectar colisiones o como una zona de acción demarcada. • Rigidbody. Convierte el GameObject en un objeto físico. Con él podemos controlar el rozamiento, la aplicación de fuerzas o cualquier otro comportamiento que esté relacionado con el aspecto físico. • Audio Source. Dota al GameObject de capacidad para reproducir sonidos. Por supuesto, estas descripciones generales solo son un adelanto de su uso; en cada caso tendrán especificaciones que deberás tener en cuenta. Para saber qué opciones nos ofrecen los distintos componentes predeterminados de Unity bastará con que utilices el atajo al manual, del que hablamos anteriormente. A continuación vamos a describir dos componentes distintos con el fin de que entiendas cómo moverte por el manual; pero, sobre todo, cómo funcionan. Así, cuando acabemos este segundo apartado podrás crear tu primer componente. Componentes 27 2.1. Transform Recordarás que cuando introdujimos el concepto de GameObject indicamos que para que un objeto se considere como tal debe formar parte de la escena. Bien, pues el componente Transform es el encargado de hacerlo, y por eso es el único componente obligatorio para cualquier GameObject. Podrás comprobar que cada objeto que introduzcas en la escena o que crees en ella tendrá automáticamente asignado un Transform, que indicará la posición que ocupa dicho objeto. No solo posiciona al objeto, sino que también le aporta una orientación y una escala que podremos modificar mediante el uso de Transform. Dichos valores se medirán en relación con los ejes cartesianos que forman el espacio de juego. Este espacio tiene su origen en la posición (X: 0, Y: 0, Z: 0), su frente está situado en la dirección (X: 0, Y: 0, Z: 0) y la escala estándar de los GameObjects será (X: 1, Y: 1, Z: 1). Es decir, un objeto cuyo Transform indique estos valores estará situado en el centro del espacio de juego, mirando de frente en dicho espacio, y se mostrará con su tamaño original. A estos valores los llamaremos «valores globales» en cuanto que representan valores relativos a ese centro del espacio de juego. Además, mediante este componente accederemos a las relaciones de parentesco del objeto tanto superiores como inferiores (verticales) como laterales (horizontales); es decir, tendremos acceso a su objeto padre (Parent), a sus hijos (Child) y a sus hermanos (Sibling). Sabremos si un objeto tiene al menos un objeto hijo si junto al primero aparece un pequeño triángulo que sirve para desplegar una lista con los nombres de cada uno de ellos. Cada hijo será hermano del resto. Si el objeto padre no tiene padre, le llamaremos objeto raíz (Root). 28 Introducción a Unity 3D Estos hijos ya no mostrarán valores globales en sus Transforms, sino que mostrarán valores locales: aquellos que se determinan en función del padre de un objeto, es decir, los valores ya no son relativos a la posición, rotación o escala del objeto en el mundo, sino a la posición, rotación y escala de su objeto padre. Así, si tenemos un objeto raíz con posición (X: 1, Y: 2, Z: 3), este estará situado una unidad a la derecha del origen del espacio de juego (X: 1), dos unidades arriba (Y: 2) y tres hacia delante (Z: 3). Si este objeto raíz tuviera un hijo cuyo Transform mostrase los valores (X: 1, Y: 1, Z: 1), nos estaría indicando que su posición está una unidad a la derecha de su objeto padre, una hacia arriba y otra hacia delante, por lo que, en términos globales, este GameObject estaría situado en (X: 2, Y: 3, Z: 4). ! Con la rotación ocurre lo mismo. Para esta propiedad lo valores estarán indicados en grados, por lo que un objeto con rotación (X: 0, Y: 0, Z: 0) tendrá la misma orientación que uno con (X: 360, Y: 0, Z: 0). Cuando quieras rotar un objeto, fíjate en que cada uno de los valores de Recuerda esta propiedad representa un eje (X: derecha-izquierda, Y: arriba-abajo, Tres de las cinco Z: delante-detrás), por lo que las rotaciones se realizarán con respecto a herramientas ellos. Es decir, teniendo en cuenta el eje de rotación Y, el objeto girará a de la escena la derecha (con valores positivos) y a la izquierda (con valores negativos). hacen referencia al movimiento, El caso de la escala es un tanto especial, ya que debemos tener en cuen- rotación y escalado ta que los valores de la escala multiplican el tamaño de los objetos: (X: 1, de GameObjects. Al Y: 1, Z: 1) es el tamaño normal y (X: 2, Y: 2, Z: 2) es el doble. Así, el hijo de utilizarlas, fíjate en un objeto cuya escala es el doble de lo normal tendrá también el doble que se modifican los de su tamaño cuando su Transform indique (X: 1, Y: 1, Z: 1) en su escala. valores del Transform. Queda claro entonces que un objeto con escala (X: 0, Y: 0, Z: 0) no se verá en la escena. En los párrafos anteriores hemos estado trabajando con Vector3 y seguiremos haciéndolo para hablar de las propiedades de Transform. Por ahora basta con que sepas que es un contenedor de tres valores decimales (X, Y, Z) y puedas identificarlo cuando veas tres valores de este tipo entre paréntesis. Componentes 29 Haremos hincapié en Vector3 cuando abordemos la creación de componentes. Veremos cómo crear vectores, cómo utilizarlos, qué propiedades tienen y qué métodos nos ofrecen. 2.1.1. Propiedades Una vez entiendas el comportamiento que aporta este componente a los distintos GameObjects (el de estar), verás que podemos hacer que estos se muevan modificando sus valores, y será cuestión de tiempo que quieras hacerlo automáticamente. Por eso, vamos a hacer una visita a Scripting Reference para ver todas las propiedades y comportamientos específicos que podemos utilizar de este componente. ! El primer paso será abrir el manual desde el propio componente pulsando el botón del manual en el componente. Una vez aquí, solo tenemos que hacer clic en Switch to Scripting para acceder a la ayuda de código Recuerda que nos brinda Unity 3D. Asegúrate de que estás usando la versión en También puedes inglés para evitar problemas de versiones traducidas en las que pueden acceder a Scripting faltar botones. Reference desde la página web de Una vez en la interfaz de programación de aplicaciones (o API, del inglés Unity 3D. application programming interface), tendremos acceso a toda la biblioteca de código de Unity. En nuestro caso, a todo lo que conlleva el componente Transform. En cada página referente a un componente podremos encontrar una descripción de él, sus propiedades y sus funciones. Vamos a centrarnos en alguna de las propiedades más importantes y en los métodos más representativos de Transform, por lo que habrá miembros de este componente que no tendremos en cuenta, ya sea por ser secundarios o por no ser propios del mismo, sino «compartidos» por todos los componentes. 30 Introducción a Unity 3D Cuando hablamos de propiedades en general diferenciamos entre las que podemos consultar y modificar y aquellas que son de solo lectura, es decir, propiedades que podemos consultar pero no modificar. Centrándonos en las propiedades específicas de Transform, vamos hablar de tres grupos principales: globales, locales y de parentesco. • Propiedades globales Vamos a llamarlas globales en el sentido con el que introdujimos el término hace algunos párrafos, es decir, serán propiedades globales todas aquellas cuyos valores sean relativos al punto de origen del espacio de juego. Encontraremos variables modificables, como position, rotation, eulerAngles o lossyScale, y variables de solo lectura, forward, right o up. ýý position. Indica o configura la posición que ocupa el GameObject en valores globales. Es decir, podemos utilizar esta propiedad tanto para saber dónde está el objeto como para cambiar su posición. ýý rotation. Indica o configura la rotación del objeto con cuatro valores de entre 0 y 1 (quaternion o cuaternión) en valores globales. Para utilizar esta propiedad tendremos que manejar la estructura Quaternion y pensar en los valores en pi radianes, es decir, en medio giro (180°). Será la forma en que veamos la rotación si utilizamos el editor en modo debug. ýý eulerAngles. Indica o configura la rotación del GameObject con tres ángulos en valores globales. En este caso trabajaremos sobre la rotación con valores eulerianos, es decir, con ángulos de 0 a 360°. Será la forma estándar en que se nos mostrará la rotación en el editor. ýý lossyScale (solo lectura). Indica la escala en valores globales, es decir, el tamaño relativo al tamaño normal del objeto. El valor de esta propiedad representa la escala del objeto multiplicada por cada uno de los valores X, Y y Z de los objetos padres, de forma que, en la práctica, tendremos un valor «global» de la escala del mismo. Un ejemplo sería el de un objeto con un solo padre cuya escala fuera (X: 2, Y: 8, Z: 0.5) y la de su objeto raíz fuera (X: 2, Y: 2, Z: 2). El valor de lossyScale sería de (X: 4, Y: 16, Z: 1). ýý forward (solo lectura). Indica el punto que se encuentra a una distancia de una unidad por delante del objeto en valores globales Componentes 31 teniendo en cuenta su rotación; es decir, si estamos en la posición (X: 0, Y: 0, Z: 0) con una rotación (X: 0, Y: 0, Z: 0), el valor de forward será (X: 0, Y: 0, Z: 1). A una misma rotación y distinta posición, por ejemplo, position = (X: 5.7, Y: 2.3, Z: 11.2), el punto forward será (X: position.X + 1 = 6.7, Y: position.y = 2.3, Z: position.z = 11.2). Volvamos al punto (X: 0, Y: 0, Z: 0), pero ahora con una rotación de (X: 0, Y: 90, Z: 0): el punto forward no sería (X: 0, Y: 0, Z: 1), sino (X: 1, Y: 0, Z: 0), que es el punto del espacio que tenemos delante a una distancia de una unidad. Con esta variable podemos, por ejemplo, saber hacia dónde se dirige el objeto o consultar qué tiene delante sin necesidad de saber hacia dónde está mirando. ýý right (solo lectura). Indica el punto que se encuentra a una distancia de una unidad a la derecha del objeto en valores globales siguiendo la misma lógica que forward. ýý up (solo lectura). Indica el punto que se encuentra a una distancia de una unidad por encima del objeto en valores globales del mismo modo que las dos propiedades anteriores. • Propiedades locales Estas variables serán locales por oposición a las variables globales; es decir, trataremos con valores relativos al objeto padre con el que estamos trabajando. En este caso solo encontramos valores modificables: localPosition, localRotation, localEulerAngles y localScale. ýý localPosition. Indica o configura la posición que ocupa el GameObject en valores locales. Igual que con la posición global, podremos consultar o modificar esta propiedad, aunque en esta ocasión debemos tener en cuenta que el punto estará en relación con su objeto padre. ýý localRotation. Indica o configura la rotación de un objeto con cuatro valores de entre 0 y 1 (cuaternión) en valores locales, es decir, en relación con la rotación de su objeto padre. ýý localEulerAngles. Indica o configura la rotación del GameObject con tres ángulos en valores locales del mismo modo que localRotation pero con valores eulerianos, como vimos en eulerAngles. 32 Introducción a Unity 3D ýý localScale. Indica o configura la escala del objeto en valores locales, es decir, en relación con la escala de su objeto padre. • Propiedades de parentesco Este grupo de propiedades hace referencia exclusivamente a las relaciones de parentesco de un objeto: parent, root y childCount. ýý parent. Indica o asigna el Transform padre del objeto. Si un objeto no tiene padre, este valor será nulo (o null). ýý root. Indica cuál es el objeto raíz (el padre más mayor) del objeto. Si el objeto es uno raíz —no tiene padre—, root devolverá el mismo Transform del objeto. ýý childCount. Indica el número de objetos hijos que tiene el Transform actual. 2.1.2. Métodos Las funciones, los comportamientos específicos del Transform que vamos a ver, estarán divididos también en tres grupos, pero en este caso harán alusión al movimiento, a la dirección y al parentesco del objeto. • Movimiento El método que utilizaremos para poder mover un objeto será Translate, aunque, como ya hemos visto, también podremos hacerlo modificando directamente la propiedad position. ýý Translate. Esta función indicará al objeto que se mueva una cantidad que le indiquemos entre paréntesis. Así, transform.Translate(new Vector3(1, 0, 0)) hará que el objeto que lleva ese Transform se mueva una unidad a la derecha en términos locales, aunque podremos indicarle que lo haga en términos globales. • Dirección En este caso contamos con más funciones para poder modificar la rotación del objeto: LookAt, Rotate y RotateAround. Componentes 33 ýý LookAt. Si indicamos un segundo Transform a esta función, el objeto girará hasta tener en frente este segundo Transform. ýý Rotate. Esta función hará que el objeto rote sobre sí mismo un ángulo indicado. Tendremos que usarla del mismo modo que Translate, es decir, añadiendo entre paréntesis un Vector3 que indique cuánto debe modificarse cada ángulo, de manera que transform. Translate(new Vector3(0, 90, 0)) hará que el objeto que lleva ese transform gire 90° hacia la derecha en términos locales, aunque también podremos indicarle que lo haga en términos globales. ýý RotateAround. En esta ocasión, el objeto se mueve y gira alrededor de un punto indicado, como lo hace la Tierra respecto del Sol. Para ello, indicaremos el eje en el que tiene que hacer el giro y el ángulo total de la rotación. En otras palabras, con ese punto de referencia, el objeto se moverá y rotará la cantidad que exija el ángulo en función del eje que usemos como referencia. • Parentesco ýý DetachChildren. Si hacemos uso de esta función, obligaremos al Transform a deshacer el parentesco que tiene con sus hijos. Así, estos hijos pasarán a ser objetos raíces, es decir, no tendrán padre. ýý Find. Mostrará, si existe, el Transform hijo de un objeto cuyo nombre coincida con el que pidamos. Si no existe, el valor será nulo. ýý GetChild. Esta función tiene la misma utilidad que Find, pero ahora apuntaremos un índice que será igual al del objeto hijo. En este caso, la única forma de que el resultado sea nulo es indicando un valor mayor que el número de hijos del objeto. El índice vendrá dado por el orden de los hijos: el que aparezca más arriba en la lista de hijos será el 0; el siguiente, el 1, y así sucesivamente. ýý GetSiblingIndex. Este método nos devolverá el índice del objeto en función de su padre, es decir, el orden relativo a sus objetos hermanos. ýý IsChildOf. Devuelve «verdadero» si el Transform es hijo del Transform indicado entre paréntesis. ýý SetAsFirstSibling. Sitúa el objeto como el primer hijo de su objeto padre. 34 Introducción a Unity 3D No te preocupes por dónde y cómo vamos a utilizar estas propiedades y métodos, pero es recomendable que eches un vistazo a lo que tienen en común todos los nombres de las propiedades y los métodos y a sus diferencias. A este estilo de escritura se le llama CamelCase y consiste en unir varias palabras en una sola poniendo en mayúsculas la primera letra de cada una. Además, te habrás dado cuenta de que todas las propiedades tienen nombres que empiezan en minúsculas seguidos de las funciones escritas con mayúscula inicial. Esto también es importante a la hora de trabajar con código. Esta notación permite que, con un simple vistazo, podamos diferenciar entre propiedades y métodos y que los nombres sean tan explícitos como sea necesario con el fin de que cualquiera pueda entender nuestro código (sobre todo nosotros mismos en el futuro). 2.2. Camera Antes de introducirnos por fin de lleno en el código, vamos a echar un vistazo al componente Camera, que nos dará la oportunidad de ver lo que está pasando en nuestra escena. Este camino será más superficial que el que hemos hecho con Transform, porque lo basaremos en la información que nos ofrece el manual de Unity y en la apariencia del componente en la ventana Inspector ahora que ya sabes cómo interpretar la API. Camera es un componente que convierte un objeto en una cámara al uso. Estos objetos serán los que rendericen la parte de la escena que queremos que vea el jugador y que podremos ver desde la pantalla Game. Aunque en apariencia es muy simple, podemos hacer mucho con un par de cámaras y una configuración adecuada, para lo cual tenemos que conocer bien todas sus propiedades: • Clear Flags. Sirve para limpiar los espacios vacíos de la cámara. Para entender cómo funciona tenemos que saber que la imagen (o frame) de la cámara será borrada y redibujada de nuevo. La cantidad Componentes 35 de veces que la cámara pueda borrar y dibujar nuevas imágenes será lo que conocemos como imágenes por segundo o FPS, del inglés frames per second. Bien, pues esta opción nos pide que indiquemos cómo queremos que se lleve a cabo esa transición entre imágenes, cómo deben redibujarse. Hay tres opciones para «limpiar» cada imagen: Skybox, que reflejará el skybox (una textura gigante en forma de cubo) de la escena en cualquier lugar en el que la cámara no encuentre ningún objeto; Solid Color, que reflejará un color sólido; y Depth Only, que veremos más adelante. Hay una cuarta opción que no limpia: Don’t Clear, que no borra la imagen anterior, sino que dibuja encima los objetos que encuentre. • Background. Es el color aplicado al fondo cuando indicamos que refleje un color sólido. • Culling Mask. Hay que marcar las capas que queremos que la cámara pueda ver. Así será posible crear capas transparentes a ojos del jugador que nos servirán para organizarnos mejor en nuestra escena. • Projection. Indica si queremos que la cámara renderice en modo perspectiva o en modo ortográfico. La opción Perspective (perspectiva) genera una pirámide desde el punto más cercano (cima) hasta el más lejano (base) y deforma los objetos, de forma que tenemos sensación de tres dimensiones. 36 Introducción a Unity 3D Con esta opción marcada podremos manejar el campo de visión de la cámara (o field of view) haciendo que todo parezca distinto sin mover ningún objeto de la escena. El campo de visión se refiere al ángulo de apertura de la cámara, que se observa en la pirámide de la que hablábamos antes. La opción Orthographic (ortográfica) nos muestra la escena sin profundidad, simulando una visión hacia el infinito, lo cual es perfecto para juegos 2D o interfaces de usuario. Al no tener sensación de profundidad, la lejanía de los objetos solo influirá en qué objeto se ve por encima de cuál. Con esta opción marcada podremos manejar el tamaño o size, que cambiará el tamaño de las bases del ortoedro (prisma rectangular) y se acercará o alejará del punto medio de la vista, de manera que podremos usar este valor, por ejemplo, para simular un zoom. • Clipping Planes. Son las distancias mínima y máxima a las que llega la visión de la cámara. Podremos ver las modificaciones en Scene, porque tanto la base como la cima del prisma/pirámide se acercarán o alejarán de la cámara. Este gizmo nos ayudará a ver qué objetos están dentro del campo de visión de la cámara. • Normalized View Port Rect. Cuenta con cuatro valores: dos indican el tamaño de la pantalla en base 1 (H: height [alto], W: width [ancho]) y los otros dos indican la posición de la imagen respecto de la pantalla en base 1 (X, Y). Gracias a esto podemos, por ejemplo, mostrar doble pantalla para un posible modo multijugador o mostrar distintas zonas de la escena a la vez. Lo que haremos será configurar una cámara con los valores W: 0.5, H: 1, X: 0, Y: 0 y otra con W: 0.5, H: 1, X: 0.5, Y: 0. Así, cada ima- Componentes 37 gen medirá la mitad de la pantalla de juego, mida esta lo que mida, y la segunda comenzará en la mitad. • Depth. Indica el orden en que se dibujan las imágenes de una cámara siguiendo un orden ascendente; es decir, la cámara -1 se dibujará primero; la 0, después, y así sucesivamente. Este principio es el que hace que la opción Depth Only de Clear Flag tenga sentido. Al renderizarse más tarde, la cámara que veremos será la que tenga mayor valor en Depth, porque se dibuja sobre el resto y las solapa. Si elegimos la opción Depth Only, la cámara renderizará los objetos que pueda ver, y donde no haya nada no dibujará, de manera que dejará que veamos lo que renderiza la cámara que se dibujó debajo. Para ello debemos manejar también el uso de las capas. • Target Texture. Se refiere a una textura sobre la que renderizar lo que puede ver la cámara. Entre los muchos usos que tiene esta aplicación, podemos crear un espejo, como practicaremos más adelante. • Oclusion Culling. Tener esta opción marcada es importante, porque solo renderiza lo que la cámara puede ver. De otra forma, la cámara dibujará cada objeto en la vista de atrás hacia delante y superpondrá los más cercanos. El tema de la oclusión es bastante más complejo, como el resto de propiedades: Rendering Path, que indica la forma de renderizado que usa la cámara, y HDR, que hace referencia a conceptos de iluminación. • Display. En esta opción podremos elegir sobre qué pantalla se mostrará lo que capture esta cámara, permitiéndonos utilizar la opción multipantalla de Unity. Para acabar con el componente Camera, debes saber que el rendimiento de tu juego estará ligado directamente a las capacidades gráficas que requiera, de forma que si son demasiado altas serán pocos los equipos que podrán ejecutarlo. Podemos hacer una estimación de este rendimiento desde la ventana Game pulsando el toggle Stats, como ya sabes. Ahí, entre otros valores importantes, encontrarás los FPS, que te indicarán la fluidez de tu juego. 38 Introducción a Unity 3D 2.3. Creación de componentes ! Habrás observado que, poco a poco, nos hemos adentrado en el código de Unity y podrás deducir que desde este momento será imprescindible tener ciertas nociones de programación. Es más, si las tienes, habrás Recuerda comprobado que cada uno de los componentes es en realidad una clase Un componente y que cuando hablábamos de funciones y propiedades del componente indica a un nos estábamos refiriendo a los miembros de esa clase. GameObject que lleve a cabo un Si tus conocimientos de programación son muy básicos o nulos, no te comportamiento. preocupes, porque, de todas formas, introduciremos los conceptos básicos para programar en Unity y te ofreceremos ayuda extra cuando sea necesario. 2.3.1. Lenguajes de programación La creación de componentes va a ser nuestra puerta a la personalización del editor en general y en concreto a la creación de nuevos comportamientos que se adapten a lo que queremos que ocurra en nuestro juego. Para ello, tendremos que programarlos haciendo uso de cualquiera de los lenguajes que Unity permite: C# o UnityScript. Se suele pensar que este segundo lenguaje es en realidad JavaScript, pero lo cierto es que es una modificación realizada específicamente para Unity. Esto, que es su mayor valor, se torna en su peor debilidad cuando pensamos en la programación en términos más generales por un motivo muy sencillo: aprender UnityScript es útil para trabajar con Unity, mientras que aprender C# tendrá otras muchas utilidades. En cualquier caso, ambos lenguajes se adaptan perfectamente a su uso en el editor por estar orientados a objetos, y si se conoce al menos un lenguaje de programación será siempre más sencillo adentrarse en lenguajes nuevos, porque generalmente siguen una lógica similar. 2.3.2. C# El principal motivo por el que te animamos a aprender C# es la cantidad de ayuda disponible en la red, como en las páginas de Stack Overflow, MSDN (de Microsoft) o Unity. Componentes 39 Lo cierto es que para empezar a programar en Unity no hay que tener un vasto conocimiento sobre el lenguaje en sí, ya que, como irás viendo conforme avancemos, podemos hacer muchísimo con muy poco. Por supuesto, cuanto más sepas, mayor provecho podrás sacarle al editor. Será suficiente con que sepas que una clase es un contenedor de miembros que dividiremos entre métodos y datos. Los primeros conllevan una funcionalidad, son bloques de código que indican al programa qué debe hacer. Los segundos son un grupo más amplio, pero bastará con que sepas que en esos datos podemos guardar valores, como el número de vidas de un personaje, o referencias, que nos permitirán acceder a otras clases y a sus miembros. Esta accesibilidad nos va a obligar a estar atentos constantemente a hasta dónde permitimos a una clase «exponer» a sus miembros, y lo indicaremos particularmente en cada caso con las palabras claves private (privado) o public (público). Sin embargo, habrá ocasiones en las que una clase esté pensada para utilizar buena parte de los miembros de otra, como ocurre con MonoBehaviour. El uso de esta clase hará que las que nosotros creemos se consideren componentes. Esto lo haremos por medio de la herencia, pero en realidad no necesitamos programarla, ya que, al crear un script, Unity nos genera una estructura mínima en la que ya indica, entre otras cosas, que este nuevo código está pensado para ser un componente. 2.3.3. Editor de código En caso de que creemos un componente desde cero, bastará con indicarlo junto al nombre de la clase que heredamos de MonoBehaviour con : MonoBehaviour. Llegamos a otro punto clave en la creación de componentes: el nombre. Para que Unity reconozca el componente como tal, la clase que creemos deberá tener exactamente el mismo nombre que el archivo que se genera en el proyecto. Para generar un archivo de código bastará con que despliegues el menú de crear en el proyecto y selecciones C# Script. Verás que, automáticamente, tendrás que indicarle un nombre. Una vez hecho esto, la ventana Inspector nos mostrará el texto que contiene dicho archivo y podremos acceder a él en cualquier editor de código o de texto. 40 Introducción a Unity 3D Por defecto, el editor de código que vamos a utilizar en Unity es MonoDevelop, que viene integrado en el programa, pero existe la posibilidad de utilizar otros. Para ello, debemos desplegar el menú Edit → Preferences → External tools. Aquí encontrarás la opción External Script Editor (editor de código externo). Si no añadiste Visual Studio al instalar Unity y no le has indicado la ubicación de ningún otro editor, la opción que tendrás disponible será MonoDevelop (built-in, es decir, integrado), pero podrás elegir otro localizando el ejecutable del programa en la opción Browse… 2.3.4. Programación en Unity Con nuestro script creado y abierto en el editor, veremos una estructura previa, como decíamos anteriormente. Vamos a hacer un recorrido por todo el código, de manera que puedas modificar, completar o eliminar lo que necesites. En las primeras líneas encontramos la palabra clave using, que indica que estamos haciendo uso de una librería. Para poder utilizar MonoBehaviour (la clase de la que debemos heredar), necesitamos hacer uso de la librería UnityEngine, que, además, contiene todas las clases y miembros de Unity que vamos utilizar normalmente. El resto de librerías que podemos utilizar no serán necesarias a estas alturas, por lo que puedes eliminarlas. Será suficiente con que sepas que cada una de ellas aporta nuevas funcionalidades a nuestro código. La siguiente línea de código es la que da nombre a la clase y al componente. Verás que se utilizan las palabras claves public, que indica la accesibilidad que tiene, y class, que es el tipo de elemento que queremos crear, seguidas del nombre que has dado al componente. Componentes 41 Después del nombre encontramos dos puntos (:), que indican herencia, y MonoBehaviour, que es el nombre de la clase de la que heredamos, como indicamos anteriormente. Las llaves siempre encierran un bloque de código, en este caso, todo el contenido de la clase. La siguiente línea con texto es un comentario. Fíjate en cómo se indican las líneas de comentario: hay que poner dos barras inclinadas al principio. Además, podemos crear un comentario de varias líneas escribiéndolo entre barras y asteriscos: /* indica el inicio y */ indica el final. El comentario indica que el método que hay inmediatamente debajo es el adecuado para dar los valores iniciales a las variables o referencias que contiene la clase. Este método se llama Start, es privado y no tiene retorno. Es privado siempre que tenga la palabra clave private al inicio de la declaración, ! pero también si no hay ninguna referencia a su alcance; es decir, si no hay ninguna palabra clave que indique lo contrario, Unity entenderá que el miembro es privado. Recuerda No olvides tener El tipo de retorno es el valor que tiene como resultado la ejecución de en cuenta a tus este bloque de código. En el caso de Start, que no devuelve ningún compañeros y a tu dato, se indica con void, pero podremos usar cualquier tipo de dato en yo futuro: escribe su lugar. comentarios en el código para que sea Después del nombre encontramos los paréntesis, que indican qué valo- más fácil entenderlo. res necesita el método para funcionar. En caso de que estén en blanco, estaremos diciendo que ese método no requiere ningún valor externo. El resto del código tiene la misma estructura, pero el siguiente método indica que será llamado una vez por frame. ¿Cómo podemos estar seguros de que esto será así? Unity cuenta con métodos específicos que se activarán automáticamente en función del nombre que tengan. Existe una larga lista de métodos, pero vamos a centrarnos en los que más uso tienen: Awake, Start, LateUpdate, Update, FixedUpdate y OnGUI. 42 Introducción a Unity 3D • Awake. Se llama a este método cuando se carga el objeto. Esto es, al inicio de la escena (si está activado en ella) o al activarse por primera vez. • Start. Se ejecutará justo antes de cargar el primer frame. • FixedUpdate. Ocurre una vez cada 0.02 segundos. Este intervalo puede ser modificado en la configuración del editor, abriendo las opciones de tiempo en Edit → Project Settings → Time y variando el valor Fixed Timestep. • Update. Se llama una vez por frame, por lo que cualquier bloque de código que incluyamos aquí se repetirá tantas veces como se refresque la imagen de pantalla. Es aconsejable no introducir operaciones demasiado complejas en este método para no ralentizar la carga de nuevos frames. • LateUpdate. Ocurre justo después de Update y nos servirá para ejecutar acciones en las que dependamos de bloques de código que se lleven a cabo en este. • OnGUI. Ocurre muchas veces en un frame y se utiliza para gestionar la interfaz gráfica, de ahí su nombre, graphical user interface (interfaz gráfica de usuario). Echa también un vistazo a la documentación para dar con otros métodos interesantes, como OnEnable, OnDisable u OnDestroy, entre otros. Por supuesto, estos no son los únicos métodos que podemos crear, pero sí los únicos que Unity ejecuta independientemente de nuestras intenciones. Para crear otros métodos no tienes más que añadir una línea con su firma (alcance, tipo de retorno, nombre y parámetros) y el bloque de código que quieras ejecutar entre llaves. 2.3.5. Comunicación entre clases En ese método podríamos, por ejemplo, querer escribir un mensaje en Componentes 43 consola que dijera «¡Hola, mundo!». En ese caso, haríamos uso de la clase Debug y de su método público estático Log, que recibe una cadena de texto como argumento. Una vez hecho esto, solo tendríamos que lla- mar al nuevo método en Start para que Unity imprimiera este mensaje. Lo que hemos hecho en esta línea es utilizar un método de otra clase, conocido como «comunicación entre componentes». Esta comunicación solo puede tener lugar si una clase permite a sus miembros ser visibles para otras clases mediante la palabra clave public. Si solo está marcado como público, tenemos que acceder a una instan- cia de la clase, es decir, a una versión creada de ese componente para hacer uso de él. A continuación veremos un ejemplo. Tenemos una primera clase llamada Pistola y en esta un número entero privado llamado balasRestantes con un valor inicial de 6 y un método público sin retorno llamado Disparo que, además de llevar a cabo la ! creación de una bala, resta 1 a la cantidad de balas restantes. Contamos también con una segunda clase llamada Tirador que contiene Recuerda un campo público para albergar una referencia al componente Pistola. Puedes consultar También tiene un método Update en el que llama al método Pistola los métodos y variables de un componente propio de Unity en la API. Además, más arriba en este apartado hemos estudiado los miembros de cada vez que el jugador pulsa un tecla. Esto último es posible porque Transform. Disparo es un miembro público, pero Tirador nunca podrá acceder a la 44 Introducción a Unity 3D variable balasRestantes porque es privada. De este modo, podemos acceder también a las propiedades y métodos públicos de los componentes propios de Unity, como Transform. Ahora supongamos que disponemos de una tercera clase llamada MovimientoDeBala en la que vamos a añadir a una bala la capacidad de moverse. ! Como ya sabes, Transform cuenta con un método específico para trasladar un objeto al que tenemos que indicar qué movimiento queremos que realice el objeto con Vector3. Recuerda El caso de Transform es especial a la hora de hacer referencia al compo- Si cuando utilices nente, porque, como recordarás, es un componente obligatorio. Esto un campo este no conlleva que toda clase que herede de MonoBehaviour, cualquier com- guarda una referencia ponente, tendrá acceso al Transform de su objeto solo con la palabra o el objeto al que clave transform. se refería ha sido eliminado, recibirás Por otra parte, para encontrar un componente distinto de Transform un error en consola y desde código dentro del mismo objeto solo tendrás que usar el método el componente dejará GetComponent<T>() de MonoBehaviour (T es el nombre de un compo- de funcionar. nente cualquiera) sobre el GameObject en el que quieras encontrar el componente en cuestión. Como ocurre con Transform, también tenemos una palabra clave para acceder al GameObject de un componente: gameObject. ! Es aconsejable utilizar propiedades o campos de referencia que inicialices una sola vez por si en algún momento tienes que modificar el com- Recuerda ponente al que remites. De lo contrario, tendrás que sustituir todas las referencias que hagas a lo largo del código. Puedes añadir un componente desde la ventana Inspector → Add Component o desde el menú del editor Component. Componentes 45 Así como podemos obtener una referencia al componente de un GameObject, también podemos añadirle uno nuevo. Para ello contamos con el método AddComponent<T>(), que funciona de la misma manera que GetComponent: con un componente T sobre un GameObject concreto. Una vez hecho todo esto, todavía tendrás que añadir todos los componentes a un GameObject y asignar las referencias para que el código se pueda ejecutar en modo juego. 2.3.6. Uso de los componentes desde Unity Además de las opciones que ya vimos para añadir componentes, existe otra forma de añadir un componente: arrastrarlo desde la ventana Project hasta el GameObject, ya sea en la jerarquía, en la escena o sobre el final de Inspector con ese objeto seleccionado; pero, para ello, este componente debe formar parte de nuestro proyecto, es decir, debe haber sido añadido o creado por nosotros, y por eso no hemos tratado esta posibilidad hasta ahora, que ya sabes crear un componente. Si añades el componente Tirador, verás que aparecen dos huecos en su apartado del inspector: uno con el nombre de su propio archivo de código y otro vacío. Bien, pues en este segundo hueco el componente espera que le digamos cuál es el componente Pistola del que queremos usar la función Disparo. En caso de que no asignemos ninguna referencia y entremos en el modo juego para hacer funcionar el código pulsando un botón, el editor nos avisará de que se ha producido un error. Para asignar esta referencia debemos añadir el componente Pistola de un objeto cualquiera y luego arrastrarlo al campo del componente Tirador. Otra forma de asignarla una vez que el componente esté en algún objeto de la escena es pulsar el círculo que encontramos a la derecha del campo vacío. Se abrirá una lista con todas las instancias del componente que requiere el campo y podremos seleccionar la que queramos, diferenciándolas por el nombre del GameObject al que pertenecen. 46 Introducción a Unity 3D + Si cuentas con dos componentes iguales (sean los que has creado o no), puedes copiar los valores asignados en el inspector de un componente a otro desplegando el menú de contexto y seleccionando Copy Com- Consejo Si alguna vez modificas un componente en modo juego pero no quieres perder esa modificación al salir de dicho modo, copia los valores del componente antes ponent (copiar componente) en el componente cuyos datos queramos. de parar el juego y Después haz lo mismo con el segundo componente, pero selecciona pégalos después. Paste Component Values (pegar los valores del componente). Esta pequeña utilidad nos puede ayudar, por ejemplo, a colocar dos objetos en la misma posición o, como en el caso que nos ocupa, a reproducir las referencias en otros componentes. Componentes 47 3. Escenas Cuando anteriormente hablamos de la ventana Scene definimos una escena como la organización espacial de un conjunto de objetos con sus propiedades específicas. Ahora que también sabes qué es un GameObject, podemos definirla con más de precisión. Diremos que una escena es un conjunto de GameObjects con configuraciones específicas de sus distintos comportamientos que guardan entre sí relaciones espaciales y de parentesco. Por lo tanto, para configurar una escena solo hay que añadir a la misma los objetos necesarios, adjuntarles comportamientos mediante los componentes y configurar individualmente cada uno de estos si fuera necesario. Como en cualquier programa de edición, es aconsejable ir guardando el proceso mientras trabajas para evitar contratiempos, así que intenta guardar una escena cuando empieces a configurarla. Para ello hay varias opciones. Si vamos a guardar una escena antes de empezar a trabajar en ella, podemos crearla desde la ventana Project en su menú desplegable Create → Scene. Si, por el contrario, ya hemos empezado a trabajar en ella, podemos hacer clic sobre ella en Hierarchy y elegir la opción Save Scene As, que tendrá el mismo efecto que desplegar el menú del editor File y seleccionar esa opción, cuyo atajo de teclado es Ctrl + Shift + S. Mientras trabajemos en una escena iremos guardando los progresos, ya sea en escenas nuevas (que hagan las veces de versiones) o en la misma escena para sobrescribir la antigua configuración con la actual. Para ello podemos usar la opción Save Scene en Hierarchy o el menú File, cuyo atajo de teclado es Ctrl + S. 48 Introducción a Unity 3D Ten en cuenta que, si tienes más de una escena en la jerarquía, Save Scene solo servirá para una concreta. Podrás distinguirla porque será la única cuyo nombre se muestre resaltado en negrita. Aprovecha que ya sabes hacer escenas y crea tu primer laberinto. Haz uso de los recursos estándares para añadir un personaje y todos los objetos esenciales para que se mueva (una superficie, obstáculos…). 3.1. Gestión y uso de las escenas En juego, normalmente, tendremos que crear varias escenas, que se corresponderán con distintas etapas de aquel o incluso con varias partes de una misma etapa. En cualquier caso, tendremos que saber movernos entre escenas a nivel de código, ya sea para cargar una o varias a la vez. Para que las escenas sean accesibles deben formar parte del proyecto como escenas en la construcción (o Scenes In Build). Estas escenas se encuentran listadas en el menú Build Settings, al que podrás acceder desde el menú del editor File. Esta lista estará vacía por defecto, pero podemos rellenarla añadiendo las escenas abiertas en Hierarchy con el botón Add Open Scenes. Otra opción es arrastrar todas las escenas de nuestro proyecto a esta lista y soltarlas, acción que nos servirá también para ordenarlas en función de un índice que veremos a la derecha del panel de escenas. Con nuestras escenas en esta lista ya podemos usarlas desde código y ! crear un flujo de pantallas, como, por ejemplo, Pantalla de Splash → Menú → Pantalla de carga → Pantalla de juego. Necesitaremos hacer uso de la librería SceneManagement, que nos Recuerda aportará los métodos, clases y propiedades necesarios para la gestión Indicamos el uso de de escenas. una librería al inicio del código usando la Con SceneManagement podremos obtener información de las distintas palabra clave using escenas y cargarlas, ya sea de manera individual o conjunta, como va- seguida del nombre mos a ver. Además, podremos realizar cargas asíncronas, es decir, cargar de la librería para que una escena mientras estamos en otra y hacer el cambio de escena o esta nos aporte una añadirla a la actual una vez que se haya realizado la carga. funcionalidad extra. Escenas 49 ! Cargar escenas Vamos a necesitar hacer uso de la clase estática SceneManager (al igual Recuerda que lo hicimos ya con Debug), en concreto, de su método LoadScene Las enumeraciones (CargarEscena). Este método nos da la posibilidad de indicar la escena en código suelen que queremos cargar mediante su nombre o su índice en la lista de es- empezar por 0 y cenas en la construcción. En general, es aconsejable priorizar el uso de por 1. Tu primera números enteros sobre el de cadenas de texto, así que lo recomendable sería utilizar el índice, en la medida de lo posible. escena será la escena 0, la segunda la 1, y así En caso de que añadamos un nombre o un índice que no corresponda a sucesivamente. ninguna escena, no se cargará, pero, si lo hace, pasaremos de la escena actual a la siguiente tan pronto como se ejecute la carga. Piensa, por ejemplo, en los juegos que comienzan con una pantalla de presentación que nos pide pulsar cualquier botón para comenzar a jugar o ir a la pantalla de menú. Ya podrías crear tu pantalla de espera utilizando este nuevo método y la línea de código que utilizamos para disparar en el apartado anterior. Por supuesto, la carga de la escena no tiene en cuenta qué tipo de escena estás cargando, por lo que estas líneas te servirán para acceder a un menú, a una escena del juego o a cualquier cosa que se te ocurra. Si has aprovechado este módulo para crear tu primer laberinto, quizá quieras que este forme parte de una escena y que el exterior sea otra escena distinta, evitando cargarla mientras que el jugador esté dentro. En este caso, tendrás que cargar esa segunda escena sin descargar la primera. Al mismo método LoadScene podemos indicarle como segundo parámetro el tipo de carga que queremos que realice: single (simple) o additive (aditiva). Para ello, utilizaremos la misma llamada que acabamos de ver añadiendo después del índice o del nombre de la escena una coma y LoadSceneMode.Single o LoadSceneMode.Additive, respectivamente. 50 Introducción a Unity 3D Verás que, al utilizar el segundo modo de carga, mantenemos los GameObjects de la escena en la que nos encontrábamos y añadimos los de la nueva. Cuando la escena que hay que cargar es tan grande que puede suponer un retraso en el flujo del juego (lo notarás porque la imagen se quedará congelada), es aconsejable utilizar la carga asíncrona con el fin de evitar tiempos de espera incómodos. Puedes utilizar este tipo de carga sustituyendo el método LoadScene por LoadSceneAsync, que requiere los mismos parámetros que el primero. Si has elegido el modo de carga simple, la escena anterior se eliminará tan pronto como la nueva se cargue, y si elegiste aditiva, se añadirán los nuevos GameObjects como con el método de carga normal. Escenas 51 Resumen • Unity 3D es un integrated development environment orientado a videojuegos, un software que reúne las herramientas necesarias para desarrollar programas, aplicaciones o, en el caso de Unity 3D, juegos. • Puedes hacer uso de la ayuda de Unity 3D con las referencias de código (API o Scripting Reference), el manual y los tutoriales de su página web o la tienda de Unity (Asset Store). • Instalar Unity 3D es totalmente gratuito y puedes hacerlo desde su página web. Solo necesitarás tener una cuenta de Unity que te identifique. Los planes de pago están pensados para profesionales, pero no es necesario pagar para usar Unity 3D. • Al crear un proyecto establecemos un orden de carpetas: Assets, Library y ProjectSettings. Unity 3D está dotado de gran plasticidad y esto es, en parte, gracias a su estructura de ventanas. Con ellas tendremos acceso a distintos aspectos del desarrollo del videojuego: Scene, Hierarchy, Inspector, Project, Console y Game. • Las capas y etiquetas nos ayudarán a organizar nuestro proyecto internamente. Puedes añadir, eliminar o modificar etiquetas y capas. • Además, existen recursos de Unity 3D y de terceros que puedes añadir a tu proyecto de forma individual o por paquetes. • Los componentes dotan de un comportamiento concreto a un GameObject. Podemos utilizar los que Unity nos ofrece por defecto o crear unos propios con los recursos C# Script que se generan desde la ventana Project. • El componente Transform es el encargado de posicionar, rotar o aplicar una escala a un GameObject, y por eso es el único componente obligatorio. • El componente Camera muestra la parte de la escena que queremos que vea el jugador y que podremos ver desde la ventana Game. 52 Introducción a Unity 3D • Las escenas organizan en el espacio un conjunto de objetos y guardan sus propiedades específicas. • Con estos primeros pasos ya puedes comenzar la creación de tu primer juego, pero no dejes de aprender: aún quedan muchos recursos y herramientas por descubrir. Resumen 53 Índice Esquema de contenido 3 Introducción 5 1. Integrated development environment (IDE) 7 1.1. Instalación de Unity 1.2. Creación de un proyecto 1.3. Modo juego 1.4. Ventanas 1.4.1. Scene 1.4.2. Hierarchy 1.4.3. Inspector 1.4.4. Project 1.4.5. Console 1.4.6. Project 1.5. Layers 1.6. Tags 1.7. Assets 8 10 11 11 12 14 15 17 19 19 21 22 23 2. Componentes 26 2.1. Transform 2.1.1. Propiedades 2.1.2. Métodos 2.2. Camera 2.3. Creación de componentes 2.3.1. Lenguajes de programación 2.3.2. C# 2.3.3. Editor de código 2.3.4. Programación en Unity 2.3.5. Comunicación entre clases 2.3.6. Uso de los componentes desde Unity 28 30 33 35 39 39 39 40 41 43 46 3. Escenas 48 3.1. Gestión y uso de las escenas 49 Resumen 52 Glosario 57 Índice 55 Glosario En este apartado podrás encontrar algunas de las palabras claves del módulo y sus definiciones. AddComponent: método de MonoBehaviour que añade un componente del tipo indicado a un GameObject. API: interfaz de programación de aplicaciones, del inglés application programming interface. Biblioteca en la que vamos a encontrar todos los elementos del código propio de un programa, en nuestro caso, Unity 3D. Asset: recurso. Da nombre a la carpeta en la que debemos incluir todos los recursos que vayamos a utilizar en nuestro proyecto y que, de hecho, podremos ver en la ventana Project. Además, también hace referencia a la tienda de Unity 3D, en la que podemos adquirir paquetes de recursos gratuitos o de pago. Aspect ratio: relación de aspecto general entre el ancho y el alto de una imagen. Es una de las opciones para la resolución de la pantalla de Game. AudioSource: componente que aporta a un GameObject la capacidad de reproducir un sonido. C#: lenguaje de programación que usamos para crear componentes en Unity 3D. CamelCase: forma de escritura que aglutina diversas palabras en una sola diferenciándolas mediante una mayúscula al inicio de cada palabra. Ejemplo: gameManager. Camera: componente que renderiza los objetos que encuentra en un área indicada y los muestra en la pantalla de juego (o en una textura preparada para ello). CanvasRenderer: componente que marca un objeto de interfaz para que sea visible por una cámara. Child: hijo. Relación de parentesco en la que un Transform se sitúa en la escena respecto de un objeto padre (o parent). Glosario 57 A-Z Collider: componente que hace que un objeto pueda calcular colisiones. Component: clase que aporta a un GameObject un comportamiento concreto. Console: ventana que muestra mensajes lanzados desde código, ya sean normales, advertencias (warnings) o errores (errors). Debug: clase estática desde la que podemos lanzar mensajes en la consola, además de otras utilidades, cuyo fin es encontrar posibles errores en el código. Display: pantalla. Unity tiene un sistema multipantalla que podemos controlar desde las distintas cámaras de la escena. Editor de código: programa utilizado para escribir código que aporta facilidades al desarrollador mientras programa. Generalmente son IDE, pero pueden ser sustituidos por cualquier editor de texto, perdiendo así la funcionalidad extra de un entorno de desarrollo. Función/método: bloque de sentencias (líneas de código) que recibe un nombre a fin de poder ser reutilizado a lo largo del código. Game: ventana del editor en la que se muestra lo que captan las cámaras de la escena. Además, podemos modificar en ella la relación de aspecto o la resolución y recibir información sobre el rendimiento del juego. GameObject: objeto de Unity que forma parte de una escena. Como tal, debe tener al menos un componente Transform. Con la primera letra en minúscula en el código, hace referencia al GameObject al que está adjunto el componente. GetComponent: método de MonoBehaviour que devuelve un componente del tipo indicado adjuntado a un GameObject. Gizmo: imagen representativa. En Unity hace referencia a los iconos que nos dicen que un objeto lleva añadido un componente concreto. Además, da nombre a una carpeta donde añadiremos imágenes nuevas que utilizaremos con este mismo fin. Global: relativo al mundo del juego, a su origen y rotación generales. 58 Introducción a Unity 3D GUI: interfaz gráfica de usuario, del inglés graphical user interface. Todos aquellos elementos de información o interactivos que se sitúan sobre la imagen del juego para dar o recibir información del jugador. Hierarchy: ventana del editor en la que se muestra una lista de todos los GameObjects que contiene una escena y cada una de las escenas que tenemos cargadas a la vez. IDE: entorno de desarrollo integrado, del inglés integrated development environment. Programa que contiene distintas funcionalidades que ayudan al desarrollo de software. Inspector: ventana del editor que muestra información correspondiente al objeto seleccionado en el editor. Layer: capa. Conjunto de objetos para aplicar o no sobre ellos distintas opciones. Ejemplo: ser renderizados por la cámara. Layout: configuración de las pantallas de Unity 3D. Library: carpeta de proyecto que contiene los archivos necesarios para la funcionalidad de un proyecto de Unity 3D. Light: componente que convierte un GameObject en emisor de luz. Local: relativo al Transform padre de un objeto, su posición y su rotación. Manual: ayuda de Unity 3D donde encontraremos descripciones de los componentes u opciones del editor. MeshRenderer: componente que marca un objeto 3D para que sea renderizado por una cámara. MonoBehaviour: clase que convierte a la que herede de ella en un componente. MonoDevelop: editor de código integrado en Unity 3D. Package: conjunto de recursos comprimidos en formato .unitypackage. Es la mejor forma de compartir recursos de Unity 3D y el formato en el que recibiremos cualquier recurso que adquiramos en la Asset Store. Glosario 59 A-Z Parent: padre. Relación de parentesco en la que un Transform alberga otro como hijo. Parentesco: relaciones de interdependencia en Unity 3D. Pueden ser de cuatro tipos: raíz, padre, hijo o hermano. Playmode: modo juego. En este modo la ventana Game se refresca un número de veces por segundo y tienen lugar los distintos bloques de código que recogen los GameObjects activos en sus componentes. Prefab: recurso de Unity que guarda la configuración de un GameObject fuera de la escena. Permite modificar a la vez todas sus copias introducidas en las escenas. private: palabra clave que indica que el miembro que la lleva en una clase no puede ser utilizado desde fuera de esta. ProjectSettings: carpeta de proyecto donde se guarda la información relativa a la configuración del proyecto. Puede ser modificada desde el editor: Edit → Project Setting. Project: ventana del editor que muestra el contenido de la carpeta Assets. Desde ella podemos crear o introducir nuevos recursos. public: palabra clave que indica que el miembro que la lleva en una clase es de acceso público, es decir, puede ser utilizada haciendo referencia a una instancia de la clase. Quaternion: cuaternión. Tipo que contiene cuatro valores entre 0 y 1 que representan una rotación en el espacio. Rigidbody: componente que dota a un GameObject de comportamiento físico. Root: raíz. Relación de parentesco que indica que un Transform no tiene ningún objeto padre. Scene: ventana del editor que muestra la configuración de una escena. Además, designa un conjunto de GameObjects con configuraciones específicas de sus distintos comportamientos que guardan entre sí relaciones espaciales y de parentesco. 60 Introducción a Unity 3D Script: archivo de código que contiene las órdenes que debe cumplir un programa o, en nuestro caso, un GameObject. Sibling: hermano. Relación de parentesco que une a dos Transforms cuyo padre es el mismo. Slider: objeto de interfaz que consiste en una barra de valores y un tirador que determina un valor concreto. Ejemplo: el slider o barra de ajuste que asigna una escala a la ventana Game. SpriteRenderer: componente que marca un objeto 2D para que sea renderizado por la cámara. Standard Assets: recursos estándares que Unity 3D incluye por defecto. Tag: etiqueta. Cadena de texto que se asigna a un objeto para diferenciarlo de otros. Toggle: objeto de interfaz que tiene dos posiciones, activo e inactivo. Transform: componente que sitúa un objeto en una escena en una posición con una rotación y una escala determinadas. Vector3: tipo que contiene tres variables decimales que representan un vector o un punto en el espacio. Glosario 61