• No se han encontrado resultados

Desarrollo de un juego HTML5 multijugador

N/A
N/A
Protected

Academic year: 2021

Share "Desarrollo de un juego HTML5 multijugador"

Copied!
54
0
0

Texto completo

(1)Escuela Técnica Superior de Ingenierı́a de Sistemas Informáticos Universidad Politécnica de Madrid. Desarrollo de un juego HTML5 multijugador por Robin tutor Luis. Giles Ribera. Fernando de Mingo López. Presentado en cumplimiento de los requisitos para el grado de Máster Universitario en Ingenierı́a Web Proyecto fin de máster. Julio 2015.

(2) ii. Proyecto fin de máster.

(3) iii. Este documento se publica bajo la licencia Creative Commons Reconocimiento-Compartir bajo la misma licencia 3.0 España http://creativecommons.org/licenses/by-sa/3.0/es/ Copyright © 2015 Robin Giles Ribera.

(4) iv. A mis padres, les dedico todo mi esfuerzo, gracias por todo el sacrificio puesto para que pueda estudiar..

(5) Resumen Este proyecto presenta un videojuego con una interfaz muy intuitiva y jugabilidad muy sencilla. El objetivo principal es el recreativo, esto es, el de entretener a los usuarios. Hemos decidido optar por tecnologı́as bastante populares para poder cumplir nuestro objetivo. Para satisfacer el hecho de ser entretenido, se permitió a los usuarios poder jugar el juego en lı́nea, al que nos referimos como el modo multijugador. Otro de los objetivos alcanzados con este proyecto fue el de profundizar en los fundamentos del desarrollo de juegos y el de conocer la estructura básica de un motor de juego. En concreto, nos hemos centrado en conocer los pilares básicos de la programación de juegos en HTML5.. v.

(6)

(7) Contenidos Resumen. v. Lista de Figuras. ix. Lista de Abreviaturas. xi. Agradecimientos Chapter 1 Introducción 1.1 Cocos2d . . . . . . . . . . . 1.2 Chipmunk . . . . . . . . . . 1.3 Perspectivas de los juego 2D 1.4 Asteroids (de Atari) . . . . . 1.5 Estructura de la memoria . .. xiii. . . . . .. 1 1 2 2 5 5. Chapter 2 Objetivo 2.1 Planteamiento . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 2.2 Requisitos . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .. 7 7 7. . . . . .. Chapter 3 Aspectos del desarrollo 3.1 Javascript . . . . . . . . . . . . 3.2 Node.js . . . . . . . . . . . . . 3.3 XMLHttpRequest . . . . . . . 3.4 WebSockets . . . . . . . . . . 3.5 Socket.io . . . . . . . . . . . . 3.6 Canvas . . . . . . . . . . . . . 3.7 Git . . . . . . . . . . . . . . . 3.8 Heroku . . . . . . . . . . . . . 3.9 Otros Aspectos . . . . . . . . . 3.10 Disponibilidad del Proyecto . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . . . . . . .. . . . . . . . . . .. . . . . . . . . . .. . . . . . . . . . .. . . . . . . . . . .. . . . . . . . . . .. . . . . . . . . . .. . . . . . . . . . .. . . . . . . . . . .. . . . . . . . . . .. . . . . . . . . . .. . . . . . . . . . .. . . . . . . . . . .. . . . . . . . . . .. . . . . . . . . . .. . . . . . . . . . .. 9 9 9 10 10 10 10 11 11 11 11. Chapter 4 Descripción informática 4.1 Conceptos previos . . . . . . . . . . . . 4.2 La arquitectura . . . . . . . . . . . . . . 4.3 La lógica del juego (requisito 6) . . . . 4.3.1 La tortuga . . . . . . . . . . . . 4.3.2 Los enemigos: Buggers . . . . . 4.3.3 Los proyectiles (Requisito 7 y 8) 4.3.4 Las explosiones . . . . . . . . . 4.4 Las colisiones . . . . . . . . . . . . . .. . . . . . . . .. . . . . . . . .. . . . . . . . .. . . . . . . . .. . . . . . . . .. . . . . . . . .. . . . . . . . .. . . . . . . . .. . . . . . . . .. . . . . . . . .. . . . . . . . .. . . . . . . . .. . . . . . . . .. . . . . . . . .. . . . . . . . .. 13 13 14 17 18 20 23 24 25. . . . . . . . . . .. . . . . . . . . . .. vii. . . . . . . . . . .. . . . . . . . . . ..

(8) viii. CONTENIDOS. 4.5 4.6. Los niveles . . . . . . . . . . . . . . . . El modo multijugador . . . . . . . . . . 4.6.1 Sincronización de los enemigos 4.6.2 Sincronización de los jugadores 4.6.3 Mensages con Socket.io . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. 27 27 28 31 32. Chapter 5 Conclusiones 5.1 Lı́neas futuras . . . . . . . . . . . . . . . . . . . . . . . . . . . . .. 35 35. Anexo A Detalles para configurar el juego A.0.1 Install Chromebrew (along with Ruby and Git) A.0.2 Instalar Node.js . . . . . . . . . . . . . . . . . . A.0.3 Instalar socket.io . . . . . . . . . . . . . . . . . A.0.4 Descargar el proyecto . . . . . . . . . . . . . . A.0.5 Iniciar el juego en el servidor . . . . . . . . . .. 39 39 39 39 40 40. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . .. . . . . ..

(9) Lista de Figuras 1.1. Example of a figure. . . . . . . . . . . . . . . . . . . . . . . . . . .. 1. 1.2. Perspectiva isométrica . . . . . . . . . . . . . . . . . . . . . . . .. 3. 1.3. Perspectiva planimétrica . . . . . . . . . . . . . . . . . . . . . . .. 3. 1.4. Perspectiva ¾ . . . . . . . . . . . . . . . . . . . . . . . . . . . . .. 4. 1.5. Top-Down View . . . . . . . . . . . . . . . . . . . . . . . . . . . .. 4. 1.6. Captura del juego Asteroids de Atari . . . . . . . . . . . . . . . .. 5. 4.1. Conceptos referenciados con frecuencia en este proyecto. . . . . .. 13. 4.2. Arquitectura del código fuente . . . . . . . . . . . . . . . . . . . .. 14. 4.3. Arquitectura del orden de las clases JavaScripts . . . . . . . . . .. 15. 4.4. Flujo de las capturas de pantallas del juego . . . . . . . . . . . . .. 16. 4.5. Flujo de las capturas de pantallas del juego en modo multijugador. 17. 4.6. Sprite sheets animado de la imagen del jugador . . . . . . . . . .. 19. 4.7. Las teclas que controlan en movimiento del jugador . . . . . . . .. 19. 4.8. Rotación del jugador . . . . . . . . . . . . . . . . . . . . . . . . .. 19. 4.9. Avance del jugador . . . . . . . . . . . . . . . . . . . . . . . . . .. 20. 4.10 El jugador lanza un proyectil . . . . . . . . . . . . . . . . . . . . .. 20. 4.11 Enemigo con movimiento aleatorio . . . . . . . . . . . . . . . . .. 21. 4.12 Enemigo con movimiento de persecución . . . . . . . . . . . . . .. 22. 4.13 Enemigo con movimiento de ataque . . . . . . . . . . . . . . . . .. 23. 4.14 Proyectiles . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .. 24. 4.15 Las explosiones . . . . . . . . . . . . . . . . . . . . . . . . . . . .. 24. 4.16 El Sprite Sheet animado de las explosiones . . . . . . . . . . . . .. 25. 4.17 Las colisiones: sin chipmunk vs chipmunk . . . . . . . . . . . . .. 26. 4.18 Sincronización de los enemigos por tramos . . . . . . . . . . . . .. 29. 4.19 Arquitectura de las clases de JavaScript en el servidor . . . . . . .. 30. ix.

(10) x. LISTA DE FIGURAS. 4.20 Actualización y cálculo de las posiciones de los enemigos . . . . .. 31. 4.21 La conexión del usuario con el servidor . . . . . . . . . . . . . . .. 32. 4.22 La conexión del usuario con el servidor: nuevo jugador . . . . . .. 33. 4.23 Bucle principal de sincronización del servidor . . . . . . . . . . .. 33.

(11) Lista de Abreviaturas HTTP. Hypertext Transfer Protocol (protocolo de transferencia de hipertexto).. URL. Uniform Resource Locator (Localizador uniforme de recursos).. JSON. JavaScript Object Notation (Notación de Objetos de Javascript).. XML. eXtensible Markup Language (lenguaje de marcas extensible).. AJAX. Asynchronous Javascript And XML (Javascript Ası́ncrono y XML).. XHR. XMLHttpRequest.. HTML. HyperText Markup Language (lenguaje de marcas de hipertexto).. RAD. Rapid Application Development (Desarrollo rápido de aplicaciones).. API. Application Programming Interface.. xi.

(12)

(13) Agradecimientos En primer lugar, agradecer a mis padres, sin su esfuerzo y colaboración esto no hubiese sido posible. Mi familia desde el otro lado del charco, por el ánimo y la alegrı́a que me muestran dándome la energı́a necesaria para seguir adelante. Agradecer también a los compañeros del trabajo, por los momentos de risa que pasamos. También agradecer a mis compañeros de piso, Youssef y Dani, gracias por la amistad y por estar ahı́ en los momento de estrés. Por último agradecer también a profesores, compañeros y amigos de la Universidad y todos los que me permitieron llegar hasta aquı́.. Robin Giles Ribera Universidad Politécnica de Madrid Julio 2015. xiii.

(14)

(15) CAPÍTULO 1. Introducción El proyecto está enfocado en profundizar en el desarrollo de un juego sencillo para la web en HTML5. En este capı́tulo hablaremos sobre el motor de fı́sica que hemos usado, Cocos2d, También conoceremos la librerı́a de fı́sica chipmunk de cocos2d y por último hablaremos sobre las perspectivas de los juegos en 2d.. 1.1. Cocos2d. Cocos2D es un framework utilizado para construir juegos en 2D, demos y otras aplicaciones gráficas/interactivas. Es una librerı́a OpenSource que permite crear juegos multiplataformas. Uno programa el juego en un lenguaje, por ejemplo en JavaScripts, y cocos2d permite exportar a Android, iOS, etc. La filosofı́a de los creadores de esta librerı́a se basa en que los desarrolladores dejen de preocuparse por la parte compleja del back-end para centrarse en el desarrollo del juego en sı́, ahorrando tiempo y dinero.. Figure 1.1: Example of a figure.. Existen dos versiones bien diferenciadas de cocos2d, la versión escrita en C++, con el nombre de cocos2d-x, y la versión HTML5, con JavaScript, con el nombre de 1.

(16) ´ CHAPTER 1. INTRODUCCION. 2. cocos2d-js. Pese a la popularidad de cocos2d-x, esta librerı́a carece de accesibilidad en los navegadores. Estamos en una era en la que los juegos HTML5 se están convirtiendo cada vez más importante en la industria de los videojuegos, especialmente en las plataformas móviles. Es por ello, que la versión de cocos2d en versión HTML5 viene a suplir esta carencia, ya que se trata de un motor de juego 100% HTML5, el cual está basado en el Canvas/WEBGL. Además, la versión de JavaScript, se supone que ofrece la misma funcionalidad que la versión en C++. Es por ello que esta versión es la ideal, incluso si se quiere ejecutar también para plataformas como Android e iOS. Dado que nosotros estamos interesados en desarrollar juegos casuales para la web, solo nos hace falta la versión de Cocos2d-js Lite, mucho más ligeras. Entre las principales caracterı́sticas generales del framework se encuentran las siguientes: • Fácil manejo del control del flujo entre diferentes escenas. • Manejo eficiente de sprites. • Transiciones elegantes (con estilo) entre escenas • Intérprete Python incluido (no incluido en la versión Lite) • También incluye otros productos: como Cocos Studio, Cocos IDE, and Cocos Shop que permiten ahorrar tiempo y dinero.. 1.2. Chipmunk. Se trata de una librerı́a de fı́sica escrita principalmente en C (también existe en JavaScript), forma parte de cocos2d como una extensión. Esta librerı́a permite que los objetos se comporten como objetos de la vida real, ya que pueden verse afectados por la gravedad, pueden colisionar con otros objetos, pueden rebotar, etc. Todo empieza en el espacio de chipmunk, para tener los objetos fı́sicos que ofrece, debemos añadir nuestros objetos a este espacio, además de indicarles la fuerza de gravedad, fricción, masa, velocidad, entre otras, para simular la fı́sica de los objetos de manera aproximada a la fı́sica que presentarı́a ese objeto en el mundo real. Principalmente se usa para detectar colisiones.. 1.3. Perspectivas de los juego 2D. El problemas de las perspectivas en juegos 2D es muy frecuente (1)..

(17) 1.3 Perspectivas de los juego 2D. 3. La perspectiva más simple es la Axonométrica. En esta representación del espacio, un objeto es representado con tres coordenadas (X, Y y Z). Existen un infinito número de perspectivas axonométricas, debido a que los diseñadores pueden colocar los tres ejes en la dirección que deseen. Por ejemplo, en la figura podemos apreciar la perspectiva isométrica, en la cual el eje Y deberı́a formar 30º con la horizontal.. Figure 1.2: Perspectiva isométrica. En esta otra figura vemos la perspectiva planimétrica. Esta vez, el eje Y forma 45º con la horizontal.. Figure 1.3: Perspectiva planimétrica. Luego tenemos la famosa perspectiva ¾, en donde el eje Y se confunde con el eje Z..

(18) ´ CHAPTER 1. INTRODUCCION. 4. Figure 1.4: Perspectiva ¾. Perspectiva Top-Down. Figure 1.5: Top-Down View. También se refiere a veces como vista de pájaro (bird’s-eye view), Overworld , vista aérea o la vista del helicóptero, cuando se usa en los videojuegos se refiere a un ángulo de cámara que muestra el jugador y el área alrededor de ellos desde arriba (figura 1.5). Esta es la perspectiva que hemos usado..

(19) 1.4 Asteroids (de Atari). 1.4. 5. Asteroids (de Atari). Figure 1.6: Captura del juego Asteroids de Atari. Asteroids es un juego minimalista de arcade, del género tiros, creado en 1979 por Atari, Inc. El jugador controla una nave espacial, durante el juego, asteroides y platillos voladores van apareciendo por la pantalla, el objetivo es el de disparar y destruir estos objetos, con la precaución de no colisionar con ellos. El punto de vista del juego es en dos dimensiones, los asteroides se mueven en diversas direcciones de la pantalla, por ejemplo, los asteroides que se van fuera de la pantalla por el borde superior, aparecen por la parte inferior moviéndose en la misma dirección. Los platillos voladores aparecen periódicamente por la pantalla y además disparan a la nave del jugador. El jugador empieza con 3 vidas y gana una vida extra por cada 10,000 puntos. El juego aumenta de dificultad aumentando el número de asteroides. Si el jugador pierde todas sus vidas, el juego termina.. 1.5. Estructura de la memoria. El presente trabajo se divide en 4 capı́tulos:.

(20) 6. ´ CHAPTER 1. INTRODUCCION. En el Capı́tulo 1, “Introducción”, como ya pudimos apreciar, detallamos principalmente el motor de juegos que usamos en este proyecto, además explizamos algunas de las perpectivas que existen en el mundo de los juegos 2d, y hablamos del juego Asteroid de Atari, que tiene ciertas similitudes con este proyecto. En el capı́tulo 2, describimos el planteamiento y el objetivo del proyecto, además de los requisitos necesarios para la consecución del mismo. En el capı́tulo 3, explicamos las principales tecnologı́as y herramientas utilizadas en el proyecto y se muestra cómo acceder al código de la aplicación. En el capı́tulo 4, describimos y explicamos toda la implementación desarrollada del proyecto. En el capı́tulo 5, extraemos las conclusiones respecto a los requisitos cumplidos y se propone trabajos futuros sobre este proyecto..

(21) CAPÍTULO 2. Objetivo En este capı́tulo describiremos el planteamiento principal del proyecto, además pasaremos a enumerar los requisitos que debemos cumplir para la consecución de los objetivos del mismo.. 2.1. Planteamiento. El proyecto está enfocado en implementar un juego sencillo para navegadores web, en HTML5 en especial, principalmente por la caracterı́stica multiplataforma de esta tecnologı́a. Ası́ que uno de nuestros primeros pasos es el de definir las reglas del juego a desarrollar. Esto nos llevará a conocer la arquitectura básica de los juegos. Para desarrollarlo, nos apoyamos en el motor de fı́sica Cocos2d, en su versión de JavaScript. Como segundo objetivo, tenemo la misión de conseguir que nuestro juego sea multijugador, esto es, que los jugadores jueguen en lı́nea al mismo tiempo a través de la red. Para ello debemos de estudiar las tecnologı́as disponibles que nos facilitarán dicha tarea. Tanto una tecnologı́a de servidor y una de comunicación para sincronizar a los diversos usuarios.. 2.2. Requisitos. A raı́z del planteamiento anterior podemos desglosar los principales requisitos en los siguientes puntos: 1. Disponer de un menú principal que nos permita navegar por los escenarios del juego. 2. Poder iniciar el escenario del juego desde el menú principal. 3. Poder iniciar el escenario del juego desde el menú en modo multijugador.. 7.

(22) 8. CHAPTER 2. OBJETIVO. 4. Tener siempre la posibilidad de volver al menú principal, es decir implementar un botón que siempre se encuentre visible, el cual nos lleva al menú principal. 5. Visualizar las puntuaciones máximas obtenidas. 6. Definir las reglas y lógica del juego a desarrollar. 7. El usuario puede disparar a enemigos. 8. Los enemigos pueden también disparar al jugador. 9. Finalizar la partida en modo único jugador. 10. Finalizar la partida en modo multijugador..

(23) CAPÍTULO 3. Aspectos del desarrollo A continuación describiremos la principales tecnologı́as que hemos utilizado en el proyecto. Indicaremos la disponibilidad del proyecto, en cuanto al código fuente y la aplicación en funcionamiento, a la vez que mencionaremos alguno aspectos del desarrollo.. 3.1. Javascript. Javascript: Es un lenguaje de programación orientado a los navegadores, porque fue ahı́ donde se originó y donde goza de la mayor popularidad.La mayorı́a de los lenguajes de programación que hacen uso de la web, hacem uso de JavaScript. AL ser de distribución gratuita y multiplataforma, también se está usando para crear aplicaciones y para el uso en servidores.. 3.2. Node.js. Node.js (a partir de ahora Node) es un programa de servidor basado en el motor JavaScript V8 (es el motor ultrarápido escrito en C++ que usa Google Chrome). Gracias a JavaScript, Node utiliza lo que se llama programación orientada a eventos, permite escribir código que es potencialmente no bloqueante. Es decir, que Node está diseñado para situaciones en que se espere una gran cantidad de tráfico y donde la lógica del lado del servidor y procesamiento requeridos no sean necesariamente grandes antes de responder al cliente. Node tiene una gran comunidad muy activa y en constante crecimiento, goza de muy buena popularidad y existen un un centenar de módulos que extienden su funcionalidad (desde plantillas, APIs, conexiones seguras, bases de datos, gestores de contenido, etc.). Adicionalmente tenemos el Node Package Module (NPM), una forma integrada de instalar y administrar los módulos de Node, asegurando que cualquier módulo se instale correctamente.. 9.

(24) 10. 3.3. CHAPTER 3. ASPECTOS DEL DESARROLLO. XMLHttpRequest. Actualmente las aplicaciones web son muy dinámicas, permiten actualizar parte de las páginas, sin que el mismo usuario tenga que refrescar la página, es lo que se llama como el método Ajax (Asynchronous Javascript And Xml). XMLHttpRequest (XHR) es el corazón de Ajax, es una interfaz empleada para realizar peticiones HTTP y HTTPS a servidores Web. La interfaz se implementa como una objeto JavaScript en el cliente, del cual se puede generar tantas instancias como se necesite para manejar el diálogo con el servidor. La información intercambiada entre el cliente y el servidor puede estar en múltiples formatos, además de XML, texto, HTML y JSON. Principalmente se usa para proporcionar contenido dinámico y actualizaciones ası́ncronas en aplicaciones web.. 3.4. WebSockets. Es una de las caracterı́sticas de HTML5. El protocolo HTTP fue concebido desde sus orı́genes para ofrecer comunicaciones en un sólo sentido, desde el servidor hacia el cliente. Sin embargo las aplicaciones web de hoy en dı́a demandan más que eso para poder ofrecer una experiencia de usuario más rica, necesitan flujo de información en ambos sentidos. Los WebSockets permiten crear un canal de comunicación que es bi-direccional, economizando recursos y reduciendo latencias. Está diseñada para ser implementada en navegadores y servidores web, pero puede utilizarse por cualquier aplicación cliente/servidor.. 3.5. Socket.io. Se trata de una librerı́a para comunicación web en tiempo real. Es una librerı́a escrita en JavaScript principalmente para Node.js, la cual permite una comunicación bidireccional entre cliente y servidor. Para ello se basa principalmente en Websockets, pero también puede usar otras alternativas como sockets de Adobe Flash, JSONP polling o long polling en AJAX. En el polling el cliente se mantiene haciendo preguntas al servidor sobre un determinado evento.. 3.6. Canvas. El canvas es un elemento de HTML5 que permite manipular los pixeles en un área en particular, permite dibujar formas, imágenes, vı́deos y animaciones..

(25) 3.7 Git. 3.7. 11. Git. Es un software de control de versiones creado originalmente por Linus Torvalds, diseñado para manejar proyectos muy grandes con velocidad y eficiencia, pero igual de apropiado para repositorios pequeños. GitHub es una de las razón de la popularidad de Git, es un excelente servicio de alojamiento de repositorios de software que utiliza Git para el mantenimiento y versionado del código fuente, añadiendo una serie de servicios extras para la gestión del proyecto y el código fuente.. 3.8. Heroku. Es un servicio PaaS (Platform as a Service), una plataforma como servicio de computación en la Nube, en principio solo soportaba el lenguaje de programación Ruby, pero posteriormente se ha extendido el soporte a Java, Node.js, Scala, Clojure y Python. La base del sistema operativo es Debian y el despliegue de la aplicación se hace a través de Git. Su filosofı́a es la de que el programador emplee su tiempo desarrollando la aplicación y no configurando servidores o preocupándose del despliegue.. 3.9. Otros Aspectos. Estas son las principales tecnologı́as que hemos usado en nuestro proyecto. Para empezar, JavaScript es el lenguaje, el único que hemos usado, en el que está escrito prácticamente todo el código fuente del proyecto. Hemos usado el control de versiones pese a que se ha trabajado en solitario, Git es una herramienta que permite disponer de copias de seguridad del proyecto, tener la capacidad de volver hacia atrás, son caracterı́sticas muy útiles durante el desarrollo del software. Otro motivo para el uso de Git, es que este es necesario para usar con Heroku. Heroku es el el servidor en la nube donde hemos alojado nuestra aplicación. Para ello hemos usado Node.js como servidor (2). Hemos tenido un problema con socket.io en Heroku, en lugar de usar websockets, heroku utiliza comunicaciones por XMLHttpRequest, no sabemos el por qué de esto, pese a ello, el juego no se ve afectado.. 3.10. Disponibilidad del Proyecto. Hemos clonado el proyecto de cocos2d-js1 , el cual se encuentra en Github. Nosotros también hemos alojado el código fuente allı́. Por otra parte, también tenemos la aplicación en funcionamiento alojada en Heroku. 1. https://github.com/cocos2d/cocos2d-js.

(26) 12. CHAPTER 3. ASPECTOS DEL DESARROLLO. # Source code https://github.com/robinparadise/turtle vs buggers # Aplicación turtle-vs-buggers.herokuapp.com.

(27) CAPÍTULO 4. Descripción informática En este capı́tulo detallaremos todas las caracterı́sticas implementadas, entre ellas, todas las que darán solución a nuestros objetivos y requisitos, explicando las tareas que fueron necesarias para implementarlas. Durante el desarrollo podemos diferenciar dos partes. Por un lado tenemos el desarrollo del juego (modo único jugador), y por otro el desarrollo del juego en modo multijugador. A pesar que durante el desarrollo hubo etapas en las que las dos partes fueron desarrolladas paralelamente (único jugador y múltiples jugadores), en el capı́tulo explicaremos en la medida de lo posible, primero las caracterı́sticas relacionadas con el modo único jugador y luego las caracterı́sticas del modo multijugador.. 4.1. Conceptos previos. Figure 4.1: Conceptos referenciados con frecuencia en este proyecto.. 13.

(28) ´ INFORMATICA ´ CHAPTER 4. DESCRIPCION. 14. Antes de pasar a la descripción, debemos de explicar conceptos que usaremos con mucha frecuencia y que son imprescindibles para el correcto seguimiento de lo que describiremos en este capı́tulo. Usaremos con mucha frecuencia nombres y sinónimos de los objetos que nos encontramos en el juego. Por ejemplo, como se puede apreciar en la figura 4.1, a la tortuga nos referiremos con el nombre de jugador, es por supuesto, el objeto controlado por el usuario. A los insectos los llamaremos principalmente enemigos, aunque también nos referiremos a ellos con el nombre de monstruos (ası́ los llamamos en el código fuente) o con el nombre de buggers (en relación al nombre del juego y los nombres de las imágenes que representan a estos objetos). Luego tenemos los proyectiles, también nos referimos a ellos cuando los enemigos o el jugador realizan un ataque, es decir, lanzar un proyectil es sinónimo de realizar un ataque. Por último, debido a la forma en que se llama en cocos2d, a todos estos objetos también nos referiremos por el nombre sprite, cuando nos referimos principalmente a la imagen que representan. Las imágenes de los sprites están sacados de openClipArt [6]. 4.2. La arquitectura. Figure 4.2: Arquitectura del código fuente.

(29) 4.2 La arquitectura. 15. En la figura 4.2 podemos apreciar la arquitectura del código fuente. Empezando por el archivo html principal (index.html), en el cual se encuentra definido el canvas (una de las caracterı́sticas de HTML5 que ya explicamos anteriormente) y también se indican los archivos JavaScripts a descargar. En estos archivos, se empieza por los archivos relacionados con el engine de Cocos2d, luego tenemos el archivo de configuración ( config.js) en el cual se definen aspectos relacionados con el juego, tales como los niveles que tiene el juego, los jugadores, el número de enemigos, la velocidad, la salud, etc. Luego tenemos las capas y escenas del juego (llamado “scene” y “layer”). La principal escena es la de game.js, en la cual transcurre el juego, luego tenemos la escena del menú principal (sysMenu.js), y el resto en las que, por lo general, se muestran mensajes de texto, como la de gameOver.js, about.js, highscores.js, etc. Otros archivos javascript importantes son los sprites, que son los objetos visuales que aparecen en el juego, como el jugador (playerSprite.js), los enemigos (monsterSprite.js), las explosiones (explosion.js) y los proyectiles (projectileSprite.js). Luego tenemos las clases de los movimientos, encargados de los movimientos de los enemigos. Por último, tenemos el resto de clases, como la de levelManager.js, encargada de los niveles del juego; la clase scoreLabel.js, encargada de la puntuación del juego; y por último la clase multiplayer.js, encargada de comunicarse con el servidor apoyándose en la librerı́a socket.io.. Figure 4.3: Arquitectura del orden de las clases JavaScripts. En la figura 4.3 podemos apreciar la arquitectura en relación al orden y lugar donde se usan las clases. Empezando por la escena del menú (la cual cumple nuestro.

(30) 16. ´ INFORMATICA ´ CHAPTER 4. DESCRIPCION. requisito 1), en este escenario se puede iniciar el escenario de juego (game, requisito 2), el escenario de las puntuaciones (highscore, requisito 5) o el escenario about. El escenario del juego hace uso de las siguientes clases: la clase multijugador, en caso de que se haya seleccionado esta opción desde el menú principal (requisito 3); se hace uso del scoreLabel, para mostrar la puntuación del usuario; también hace uso de la clase levelManager, la cual se encarga de añadir el sprite del jugador y los sprites de los enemigos en el escenario del juego. Cuando el escenario del juego termina (requisito 9), pueden ocurrir dos escenarios: se muestra el escenario de message, indicando el siguiente nivel o se muestra el escenario gameOver, indicando el final del juego.. Figure 4.4: Flujo de las capturas de pantallas del juego. En la figura 4.4 podemos observar el flujo de los distintos escenarios del juego. Siempre se muestra el menú principal en el inicio, en este, el usuario del juego elige entre inicar el escenario del juego (ya sea modo único o multijugador), entre iniciar el escenario de las puntuaciones o iniciar el escenario del about (acerca del juego). En estos tres escenarios, tenemos la posibilidad de volver al menú principal desde un botón en la esquina superior derecha (requisito 4). Desde el escenario del juego, podemos mostrar el escenario message o el escenario gameOver, estos se muestran durante un espacio de tiempo suficiente para que el usuario pueda leer el mensaje que se le muestra. El escenario message muestra la información acerca del siguiente nivel, es por ello que volvemos a iniciar de nuevo el juego después que se haya mostrado. En cambio, cuando mostramos el escenario de gameOver, volvemos al menú principal, dado que el juego ha acabado (requisito 10)..

(31) 4.3 La lógica del juego (requisito 6). 17. Figure 4.5: Flujo de las capturas de pantallas del juego en modo multijugador. Existe una pequeña diferencia en el escenario del juego en el modo multijugador. Dado que en el modo multijugador no existen niveles, cuando el escenario del juego termina, puede ocurrir dos escenarios: el escenario gameOver o el escenario highscore. En caso de que el jugador pierda el juego debido a que ha muerto en el juego, se vuelve al menú principal, de igual manera que ocurre en el modo único jugador, es decir, se inicia el escenario de gameOver con el mensaje en concreto durante un espacio de tiempo determinado y luego de forma automática se vuelve al menú principal. En cambio, si el jugador acaba el juego multijugador (gane o pierda), se pasa al escenario de highscores indefinidamente, hasta que el usuario decida volver al menú principal.. 4.3. La lógica del juego (requisito 6). Se trata de un juego muy simple. El usuario controla una tortuga, siempre se empieza en el centro de la pantalla, el equivalente a la nave espacial en el juego de Asteroids, con la que igualmente puede disparar, en nuestro caso, lanzar proyectiles. El escenario del juego sucede en lugares recónditos del universo, por las imágenes de galaxias lejanas que apreciamos. Igualmente, si en Asteroids aparecı́an asteroides y platillos voladores, en nuestro juego también aparecen enemigos, eso sı́, en forma de insectos, a los cuales les llamamos buggers (de ahı́ el nombre de nuestro juego: Turtle vs Buggers). El principal objetivo del juego es que el usuario destruya a todos los enemigos. El juego es bastante corto, solo tres niveles, en contraste con Asteroids, el cual no tiene fin en cuanto a niveles. Los enemigos aparecen periódicamente, existen enemigos muy fáciles de destruir, los cuales siguen una trayectoria aleatoria, luego están los que constantemente persiguen al jugador y por último tenemos los que atacan lanzando proyectiles al jugador. El juego se inicia con la salud al 100%, y este va aumentando.

(32) ´ INFORMATICA ´ CHAPTER 4. DESCRIPCION. 18. de dificultad en cada nivel, aumentando el número de enemigos y el tipo de enemigos que aparecen, además de aumentar la velocidad del juego. Si la salud del jugador se acaba, el juego termina. La perspectiva es en dos dimensiones, con un punto de vista en Top-down. Además, los objetos del juego no pueden salir del escenario, es como si se encontraran encerrados en la pantalla, esta es una de las grandes diferencias con el juego Asteroids de Atari. Los personajes que aparecen en el escenario del juego son los que describimos a continuación:. 4.3.1. La tortuga. Es el objeto controlado por el jugador, para este hemos definido su velocidad en función de la frecuencia de actualización del juego, es decir, como tenemos configurado nuestro juego para que funcione a 60 herzios, esto es, que nuestro juego se actualiza cada 0.016 segundos aproximadamente. Si indicamos que nuestro jugador se mueve a 2 pixeles por cada paso, lo que estamos diciendo es que su velocidad es de 120 pixeles por segundo. En el tercer nivel y en el modo multijugador, el jugador se mueve a 3 pixeles por cada paso. Para crear la animación de la tortuga, con el objetivo de que parezca que se está moviendo (3), Cocos2d proporciona con su API una forma fácil de crear animaciones, las cuales llama Sprite Sheets, que no es más que una imagen más grande que la original, en la que ponemos nuestro sprite (nuestra imagen de la tortuga), por supuesto, ponemos varios de nuestros sprites ligeramente modificados para que dé la sensación de que la imagen está en movimiento en cada salto. Además, viene con un archivo de texto (con la extensión .plist), en el cual se especifica las posiciones de los diferentes sprites que se ha añadido al Sprite Sheet. La razón de su uso se debe, principalmente, a que Cocos2d está optimizado para ello, es mucho más rápido que si se usara imágenes animadas tipo GIF (las cuales no están soportadas [5]), o hacer las llamadas manualmente para cambiar la imagen. Existe un programa para crear estos Sprite Sheets animados, el programa se llama Texture Packer, pero no hemos podido hacer uso de él (además de que se trata de un programa de pago). Es por ello que hemos decidido crearlo manualmente, tanto el sprite sheet, ası́ como el archivo donde se especifica la posición de cada sprite. El resultado final se puede ver en la figura 4.6..

(33) 4.3 La lógica del juego (requisito 6). 19. Figure 4.6: Sprite sheets animado de la imagen del jugador. Para controlar el movimiento de la tortuga necesitamos de un teclado:. Figure 4.7: Las teclas que controlan en movimiento del jugador. Con las teclas de las flechas izquierda y derecha se controla el movimiento de rotación del objeto (ver figura 4.8).. Figure 4.8: Rotación del jugador. Con las teclas de las flechas arriba y abajo se controla el movimiento de avance hacia adelante y hacia atrás en función de la rotación que disponga el objeto. Se puede combinar el uso de las fechas para realizar un movimiento curvilı́neo (figura 4.9)..

(34) ´ INFORMATICA ´ CHAPTER 4. DESCRIPCION. 20. Figure 4.9: Avance del jugador. Con la tecla de la barra espaciadora se realizan disparos de proyectiles hacia la dirección a la que apunta la tortuga (figura 4.10), la cual cumple el requisito 7.. Figure 4.10: El jugador lanza un proyectil. 4.3.2. Los enemigos: Buggers. Son un total de 3 enemigos, cada uno con un tipo de movimiento y ataque distinto. Para destruirlo es necesario que un proyectil lanzado por el jugador los alcance. Bugger 1: Aparece en el nivel 1, es el enemigo más fácil de destruir, su movimiento es aleatorio y prácticamente no molesta al jugador. En la figura 4.11, podemos ver una aproximación del movimiento..

(35) 4.3 La lógica del juego (requisito 6). 21. Figure 4.11: Enemigo con movimiento aleatorio. El movimiento consisten en ir generando números aleatorios correspondientes a puntos en la pantalla, estos corresponden a los puntos donde se dirigirá el enemigo, solo cuando llega al punto calculado sequencialmente se calcula el siguiente punto. Bugger 2: Aparece en el nivel 2, su movimiento consiste en perseguir al jugador. En la figura 4.12 podemos apreciar en qué consiste el movimiento..

(36) 22. ´ INFORMATICA ´ CHAPTER 4. DESCRIPCION. Figure 4.12: Enemigo con movimiento de persecución. El movimiento se basa en perseguir siempre al jugador, para ello, se va calculando puntos aleatorios cercanos cada cierto tiempo. Aquı́, la aleatoriedad está en la distancia, es decir, se obtiene un punto aleatorio situado entre la posición en la que se encuentra el enemigo y el punto medio equidistante entre el enemigo y el jugador. Cuando el enemigo se encuentra muy cerca, el punto objetivo es directamente la posición del jugador. Bugger 3: Aparece en el nivel 3, igual que el enemigo 2, su movimiento consiste en perseguir al jugador, pero además de manera periódica ataca al jugador lanzando proyectiles (requisito 8)..

(37) 4.3 La lógica del juego (requisito 6). 23. Figure 4.13: Enemigo con movimiento de ataque. Este es el movimiento que menor velocidad tiene. En realidad es una combinación entre el movimiento aleatorio y el de persecución, solo que además, en este se calcula el tiempo en el que el enemigo debe lanzar el proyectil para atacar al jugador. Cuando el enemigo se encuentra lejos del jugador, el movimiento y el ataque es aleatorio, tanto en tiempo como en distancia. En el caso en que el enemigo se encuentre a una distancia cercana del jugador (aproximadamente a una distancia 35% máxima del ancho de la pantalla), el punto objetivo es la posición del jugador. El ataque con el proyectil se produce en un tiempo aleatorio entre cero y un segundo, desde el momento en el que se calcula el punto objetivo.. 4.3.3. Los proyectiles (Requisito 7 y 8). Los proyectiles (figura 4.14) tienen un papel importante en el juego, tratan de manera indiferente al jugador y al los enemigos, ya que desde el punto de vista del proyectil solo existe el origen del disparo y los objetivos del proyectil, los cuales pueden ser tanto el jugador como los enemigos. Cuando el proyectil es lanzado por el jugador, se presenta de color naranja, y solo puede colisionar con los enemigos. En el caso que fuera lanzado por el enemigo, presenta un color verde oscuro, y al estar especialmente dirigido hacia el jugador, no puede colisionar con el resto de enemigos. Automáticamente se destruyen cuando sobrepasan las dimensiones de la pantalla o cuando colisionan con los objetivos a los que fue dirigido, en este último caso, producen explosiones, de las cuales se explican en la siguiente sección..

(38) ´ INFORMATICA ´ CHAPTER 4. DESCRIPCION. 24. Figure 4.14: Proyectiles. 4.3.4. Las explosiones. Las explosiones (figura 4.15) las encontramos cuando los enemigos aparecen aleatoriamente en alguna posición de la pantalla y cuando un proyectil colisiona con un objetivo (el jugador o los enemigos). El color de las explosiones depende de los personajes, cada enemigo tienen asignado un color especı́fico, el enemigo 1 tiene como color caracterı́stico el rojo, el enemigo 2 el amarillo y el enemigo 3 el verde oscuro, el jugador tiene el color por defecto de la explosión, color amarillo.. Figure 4.15: Las explosiones.

(39) 4.4 Las colisiones. 25. Podemos observar que todas las imágenes de las explosiones solo varı́an en su color. Serı́a un auténtico error tener imágenes para cada explosión que ocurre en el juego, sin contar el tiempo que nos llevarı́a crearlas. Por suerte, la API de cocos2d (4) dispone de herramientas para poder cambiar los colores de imágenes por código. Su funcionamiento es que el color de cada pixel se multiplica por un valor de tinte el cual cambiará el color del pixel, por supuesto los pixeles que son todo negro no tendrán ningún cambio, ası́ los pixeles de colores claros son los más fáciles de polarizar. La imagen de la explosión no es nada más que un Sprite Sheet, el cual ya explicamos en la sección para el sprite de la tortuga. Este Sprite Sheet lo obtuvimos de los juegos de ejemplo que Cocos2d no ofrece (en concreto, del juego Moon Warrior), en la figura 4.16 podemos ver la animación.. Figure 4.16: El Sprite Sheet animado de las explosiones. 4.4. Las colisiones. Para las colisiones hemos hecho uso de la librerı́a Chipmunk (la cual ya explicamos anteriormente). Para ello hemos definidos el espacio fı́sico con paredes donde el juego va a tener lugar. Lógicamente, dado que el juego tiene lugar en el espacio y además tenemos un perspectiva top-down, la gravedad debe ser nula. Lo único que nos interesa son las colisiones de los objetos con las cuatro paredes y las colisiones entre los propios objetos (enemigos y el jugador), para ello, añadimos los objetos al espacio simulado como objetos dinámicos, luego la librerı́a se encarga de aplicar toda la fı́sica de colisiones de forma automática por nosotros. Sin embargo, hemos hecho una excepción con los proyectiles. Estos no están definidos en el espacio fı́sico, no lo hemos hecho por el rendimiento, sino porque el control de las colisiones es mucho más sencillo sin chipmunk. Por ejemplo, queremos que los proyectiles lanzados por el enemigo no colisionen con el resto de enemigos ni con las paredes del espacio. En Chipmunk, para lograr esto, tenemos que definir el proyectil y eliminar su evento de colisión para que no tenga efecto sobre el resto de enemigos, pero de las iteraciones que la librerı́a realiza por detrás no nos libramos, para ello debemos realizar configuraciones más complejas. Es por ello que hemos.

(40) 26. ´ INFORMATICA ´ CHAPTER 4. DESCRIPCION. decidido realizar de forma tradicional el bucle de colisión para que cada proyectil itere solo sobre sus objetivos, en este caso, el proyectil lanzado por el enemigo solo itera sobre los jugadores que existen e ignora al resto de enemigos y a las paredes del espacio.. Figure 4.17: Las colisiones: sin chipmunk vs chipmunk. Como vemos en la figura 4.17, nuestra implementación de la colisión es mucho más sencilla que la forma en que trabaja chipmunk. En nuestro caso, estamos calculando la distancia entre un punto (el proyectil) y un cı́rculo (los objetivos), el cual es más fácil de entender y es un evento de colisión más rápido que el usado por chipmunk, en el que los eventos de las colisiones se utilizan rectángulos delimitadores. Además, en chipmunk todos los eventos de colisión ocurren, es por el tipo de etiqueta de los cuerpos que decidimos si deseamos ignorar la colisión o no. Obviamente, para un motor de fı́sica esto no supone ningún problema y ni siquiera deberı́amos preocuparnos por problemas de rendimiento, salvo que estemos usando miles de cuerpos a la vez en un espacio colisionando entre sı́. Simplemente decimos que se requiere de mucho más esfuerzo en chipmunk configurar los cuerpos para que se comporten de la manera en que nos gusta, es decir, que para nada estamos diciendo que los motores de fı́sica sean un mal sistema, nuestro juego es muy simple para que ocurra un problema de rendimiento de este tipo..

(41) 4.5 Los niveles. 4.5. 27. Los niveles. Para saber el momento en que debemos pasar al siguiente nivel hemos realizado un bucle que comprueba en cada momento si el jugador ha conseguido pasar el nivel, eso sı́, el bucle no está definido en el bucle principal del juego, eso serı́a un derroche de recursos, para este caso lo hemos programado cada segundo en un bucle secundario. Los niveles están definidos en un archivo de configuración. En este archivo definimos el número de enemigos a mostrar, los tipos de enemigos que disponemos, el tipo de jugador, los colores de las explosiones, cuando se debe terminar el juego y muchas otras configuraciones como la salud, el número mı́nimo de enemigos, el tiempo especı́fico en el que aparecen enemigos, etc. La configuración de la dificultad de los niveles la hemos definido en función de la velocidad de los objetos (enemigo y jugador) sobre el campo de juego, en función del número de enemigos, y por el tipo de enemigos que aparecen. En el primer nivel solo mostramos enemigos con movimiento de tipo aleatorio, muy fáciles de destruir. Se muestran un total de 4 enemigos. Si el jugador los destruye pasa al segundo nivel. El segundo nivel, el número de enemigos se incrementa a 6, y aparecen los enemigos de tipo 1 y tipo 2, con el movimiento aleatorio y el de persecución, además de incrementar la velocidad de los mismo. En el último nivel aparecen los enemigos de tipo 3, es decir, en este ya tenemos los tres tipos de enemigos en el escenario, hasta un total de 8 enemigos. En este nivel los enemigos tienen su máxima velocidad y los enemigos de tipo 3 pueden atacar al jugador. Luego tenemos el nivel multijugador, en este los enemigos son los mismos del nivel 3, pero el lı́mite de enemigos que hay que destruir para que termine el juego es de 30, El jugador que más puntuación obtenga es el ganador. La puntuación se mide por el número de enemigos destruidos, los disparos certeros y la salud del jugador.. 4.6. El modo multijugador. Para implementar la parte multijugador hemos reutilizado gran parte del código JavaScript del cliente. Se ha añadido la clase multijugador.js (mirar figura 4.3). Esta clase se encarga de la sincronización con el servidor a través de websockets apoyándose en socket.io. Para no reescribir nuevas clases, permitimos iniciar a las clases en modo jugador único o multijugador, pasándole un parámetro. De esta manera, podemos tener el objeto de la clase jugador local y una lista de objetos que representan al resto de jugadores remotos. La distinción es necesaria, ya que los jugadores remotos no neces-.

(42) ´ INFORMATICA ´ CHAPTER 4. DESCRIPCION. 28. itan, por ejemplo, el bucle de actualización ni tampoco controlar el evento de colisión con los enemigos, eso es tarea del resto de usuarios que deben controlar su propio jugador. De la misma manera necesitamos indicar que los objetos de los enemigos se inicien en modo multijugador, principalmente para que no se inicien con el movimiento que tienen asignado por defecto (aleatorio, persecución o ataque) y que tampoco se inicie el bucle de actualización que se encarga de ejecutar el movimiento. En el modo multijugador, es el servidor el que se encarga de actualizar las posiciones de los enemigos. Además de iniciar el objeto enemigo en modo multijugador, hemos creado otro tipo de movimiento, el “movimiento remoto”, el cual tiene la simple misión de tratar con las posiciones aleatorias que llegan desde el servidor para recrear los movimientos en el lado del cliente. De otra manera, serı́a casi imposible sincronizar los movimientos de los enemigos, es necesario que el servidor se encargue del movimiento de los enemigos.. 4.6.1. Sincronización de los enemigos. La sincronización de los enemigos fue la parte más compleja del desarrollo del juego. Durante el desarrollo surgieron varias aproximaciones para esta tarea: • La primera idea que surgió para sincronizar los movimientos de los enemigos, fue la de sincronizar de golpe todas las posiciones aleatorias, es decir, si pensamos en que lo único que da problemas con el resto de los jugadores son la generación de posiciones aleatorias, con este modelo se intentó sincronizar todas las posiciones aleatorias generadas desde el servidor con todos los usuarios conectados. Por ejemplo, enviamos en ráfagas de periodos largos la lista, por poner un ejemplo, con 1000 posiciones aleatorias; en un mundo ideal, en el que los jugadores se sincronizan a tiempo, todos deberı́an ver exactamente el mismo mundo. Para solucionar los problemas de sincronización cuando los usuarios se conectan a destiempo, el servidor calcuları́a e indicarı́a la posición y el espacio de tiempo por el que va el juego. Pese a lo complejo y extraño que parece, esta idea es la que menos problemas nos ha dado de todas las que hemos descartado, de todas maneras es una idea horrible, ya que los problemas de sincronización son evidentes. Igualmente el servidor tendrı́a que saber en todo momento la situación del juego. • Otra idea por la que pasamos, fue la de intentar que exista siempre un jugador piloto que sincronice las posiciones de los enemigos, en otras palabras, que el juego se juegue del lado del cliente en un usuario conectado en concreto. De esta manera, el servidor solo se encargarı́a de difundir los mensajes al resto de.

(43) 4.6 El modo multijugador. 29. jugadores. La idea fue descartada muy rápido, dado la complejidad de asegurarse que siempre exista un usuario piloto que se encarge de la lógica del juego. • El otro modelo en que se pensó, fue el de sincronizar solo en los tramos no predecibles, es decir, cuando generamos los números aleatorio para calcular la siguiente posición del enemigo.. Figure 4.18: Sincronización de los enemigos por tramos. Este modelo también nos dio problemas de sincronización evidentes. Por ejemplo, cuando un usuario se conecta en mitad de la “no sincronización”, ver figura 4.18, la solución en este caso es la de sincronizar también cada vez que un usuario se conecte. Aunque la idea en teorı́a parece idónea, en la práctica lleva a problemas de sincronización, por ejemplo, cuando se producen colisiones o cuando ligeramente los enemigos van más adelantados que en el resto de usuarios, provocando que durante ratos los usuarios perciben mundos ligeramente diferentes. • Al final, la idea a la que hemos llegado (una idea que desde un principio querı́amos evitar), es la de que en todo momento exista un bucle de actualización en el servidor, actualizando todo lo necesario y principalmente, actualizando los movimientos de los enemigos. Es la idea más sencilla de implementar de todas, pese a que la evitamos desde el principio, más que todo, por el hecho de que tener un bucle de actualización nos lleva a la idea de llevar el juego entero al servidor. Aunque el hecho de que el juego se juegue en el servidor, es el modelo más aceptado y recomendado por la mayorı́a de los desarrolladores, el juego está en el servidor y los usuarios solo envı́an los eventos del teclado, ası́ los usuarios solo reciben “pantallazos” del juego. Sin embargo, este no es.

(44) 30. ´ INFORMATICA ´ CHAPTER 4. DESCRIPCION. el modelo que llegamos a realizar, pero con más tiempo es lo que hubiéramos terminado implementando. Para llegar al modelo que tenemos (figura 4.19), hemos llevado primero las clases de los movimientos de los enemigos al servidor. Dado que los movimientos hacen uso de muchas funcionalidades de la API de Cocos2d, tuvimos que volver a implementar gran parte de las funciones. Aunque otra idea serı́a llevar toda la librerı́a de Cocos2d al servidor, pero esto es algo que no quisimos hacer, aunque es perfectamente válido.. Figure 4.19: Arquitectura de las clases de JavaScript en el servidor. Si observamos la figura 4.19, mientras que en el cliente tenı́amos 3 clases de movimientos (ver figura 4.3), en el servidor la reducimos a 2 clases de movimientos (movimiento aleatorio y persecución), el movimiento de ataque ha desaparecido, esto es porque el movimiento de ataque es el mismo que el de persecución, y el lanzamiento de proyectiles los calculamos en el controlador de los enemigos (llamado monsters Controller). Este controlador se encarga de actualizar todas las posiciones de los enemigos y también de generar enemigos aleatorios cuando sean necesarios (principalmente, si hay menos de 3 enemigos en el escenario, el controlador de enemigos envı́a más enemigos hasta un lı́mite de 30 enemigos, o el que se indique en el archivo de configuración config.js)..

(45) 4.6 El modo multijugador. 31. Figure 4.20: Actualización y cálculo de las posiciones de los enemigos. El único problema que tenemos a la hora de actualizar las posiciones de los enemigos, es saber cuándo se deben calcular y actualizar las nuevas posiciones de destinos. Tenemos dos opciones aquı́, que los usuarios difundan la posición de los enemigos al servidor, o que el servidor lo calcule. La primera opción es la menos eficiente, en el caso en que existan muchos usuarios conectados, el servidor recibirı́a muchos mensajes en vano. Por tanto, la segunda opción es la adecuada, el servidor se encarga de calcular, por cuenta propia, donde deberı́an estar los enemigos, es decir, el servidor debe simular el movimiento de los enemigos. Para ello, ver figura 4.20, simplemente realizamos el cálculo de la distancia entre el punto de origen y el destino, con esta distancia y la velocidad (la cual es constante), podemos calcular el tiempo que durará el movimiento, es decir, el servidor calcula la nueva posición de destino del enemigo cuando pasa este intervalo de tiempo, que es cuando el movimiento finaliza. Si el intervalo de tiempo no se ha cumplido, tan solo calculamos la posición en la que se encuentra el enemigo, como sabemos el tiempo que ha pasado desde la última actualización, y con ese tiempo conocemos la distancia que ha recorrido el enemigo, podemos calcular el punto exacto en el que se encuentra el enemigo. Este bucle de actualización ocurre cada 250ms (es el que hemos decidido por simple observación), aunque se podrı́a reducir para tener más precisión.. 4.6.2. Sincronización de los jugadores. La sincronización del movimiento del jugador con todos los usuarios es muy simple. Cada usuario emite su mensaje de actualización cuando se producen los eventos del.

(46) ´ INFORMATICA ´ CHAPTER 4. DESCRIPCION. 32. teclado. Ası́ cuando el servidor reciba el mensaje, lo difunde al resto de usuarios. De esta manera, todos los usuarios ven de manera sincronizada todos los movimientos de los usuarios.. 4.6.3. Mensages con Socket.io. Figure 4.21: La conexión del usuario con el servidor. En la figura 4.21 podemos ver desde el punto de vista de un usuario lo que ocurre cuando se inicia el modo multijugador. El jugador envı́a el mensaje de conexión al servidor, este al recibirlo inicia eventos que escucharán a este usuario en concreto (vemos la lista de eventos en la figura bajo la caja “listeners”). Ante cualquier mensaje que emita el usuario, en el servidor existirá un escuchador para ese mensaje en concreto. El servidor procesa el mensaje recibido y los difunde al resto de usuarios conectados. Solo existe una excepción, en el caso de que el usuario emita el mensaje de actualización de la salud (mensaje “update player health”), el mensaje se procesa pero no se difunde, esto es ası́ ya que en el juego no sabemos el nivel de salud del resto de jugadores..

(47) 4.6 El modo multijugador. 33. Figure 4.22: La conexión del usuario con el servidor: nuevo jugador. En la figura 4.22, vemos con más detalle lo que ocurre después de la conexión. El usuario emite un mensaje, “new player”, indicando que se trata de un nuevo jugador (obviamente refiriéndose a sı́ mismo). Dado que se trata de un nuevo jugador, el servidor difunde el mensaje al resto de usuarios, y después envı́a al nuevo usuario los jugadores existentes y los enemigos existentes en el juego, y de esta manera el usuario queda sincronizado.. Figure 4.23: Bucle principal de sincronización del servidor. En la figura 4.23, observamos la dinámica del bucle de actualización implementado en el servidor. El servidor, en este bucle, emite mensajes a todos los usuarios conectados. Estos mensajes pueden referirse a nuevos enemigos, “new monsters”, en el juego (solo en caso de que se necesiten más enemigos), pueden referirse a la actualización de las posiciones de los enemigos, “update monster”, o la actualización la puntuación del usuario que va en cabeza, “leader”. El último mensaje que el servidor puede difundir es cuando el juego termina, “game over”, este provoca que el juego termine en todos los usuarios conectados, esto ocurre cuando ya se han destruido 30 enemigos (ası́ es como se definió en el archivo de configuración)..

(48)

(49) CAPÍTULO 5. Conclusiones Durante el desarrollo del proyecto hemos pasado por varias etapas. Desde un principio tenı́a claro con qué tecnologı́a querı́a trabajar, descarté realizar el proyecto con Cocos2d-x (en el lenguaje C++), tenı́a claro que el lenguaje deberı́a ser JavaScript. Es un acierto, dado que el equipo de desarrollo de Cocos2d está muy activo con esta tecnologı́a. El hecho de tener decidio esto, me ahorró mucho tiempo, ya que luego esto desenbocó en la decisión de usar las tecnologı́as Nodejs como servidor y socket.io para la comunicación, la popularidad de estas tecnologı́as y que casi siempre van ligadas la una con la otra, hizo que me interesara por ellas. La segunda etapa fue la más difı́cil, pasé mucho tiempo decidiendo qué tipo de juego deberı́a hacer, dado que nunca habı́a desarrollado un juego antes, por ello dediqué un gran tiempo a investigar y aprender de tutoriales. Una vez decidı́ la lógica del juego, llegó la parte divertida del proyecto, tenı́a bastantes ideas, que al final por falta de tiempo no las pude incluir. Pero la satisfacción de acabar el proyecto fue enorme. En definitiva, podemos dar por satisfecho nuestro objetivo, nos hemos familiarizado con el desarrollo y funcionamiento de videojuegos desde el inicio hasta el final. No es un trabajo fácil, se requiere de mucho esfuerzo, pero al final el resultado vale la pena.. 5.1. Lı́neas futuras. En este apartado existen un sin fin de posibilidades. Hemos descartado una gran cantidad de ideas, obviamente el tiempo es un factor que da prioridad a ciertas cosas. Principalmente, una de los aspectos que menos me gusta, es la simplicidad del juego. El juego cae rápidamente en el aburrimiento, ya que es bastante corto y además bastante repetitivo. Ası́ que, una de las lı́neas futuras está por enriquecer este apartado, con nuevos elementos interactivos, tales como, nuevos enemigos, incluir obstáculos, escenarios que se extiendan más allá de los lı́mites de la pantalla o experimentar con nuevas perspectivas, ası́ como un sin fin de posibilidades.. 35.

(50) 36. CHAPTER 5. CONCLUSIONES. También el modo jugador deja mucho que desear, no existen salas para los jugadores, no se pueden ver los nombres del resto de jugadores conectados. Uno de los aspectos más curiosos, es que no existe base de datos, la persistencia es tan solo el almacenamiento local que HTML5 nos proporciona. Incluir persistencia, principalmente en el servidor, es posiblemente una de las tareas futuras primordiales. Por último, debido al indiscutible dominio del mundo móvil, es un completo error no pensar en estas plataformas móviles. Esta es una de las lı́neas que fortalece nuestra decisión de haber elegido JavaScript, en lugar de una alternativa nativa, ya que en este aspecto es por la que Cocos2d destaca, es multiplataforma. Pese a ello, no nos ha dado tiempo a intentar siquiera probar alguna otra plataforma..

(51) Bibliografı́a 1. Pespectivas de los juegos: https://en.wikipedia.org/wiki/Video game graphics 2. Nodejs + Socket.io + Heroku: http://robdodson.me/deploying-your-first-nodedot-js-and-socket-dot-io-app-to-heroku/ 3. Animaciones con sprites: http://stackoverflow.com/questions/23140277/a-simplesprite-sheet-animation-in-cocos2d-js 4. Coloring sprites: coloring-sprites/. http://www.brandontreb.com/cocos2d-tutorial-dynamically-. 5. GIF is not supported on Cocos2d: http://discuss.cocos2d-x.org/t/how-to-displaygif/2714/7 6. Imágenes sin copyright: openclipart.org. 37.

(52)

(53) CAPÍTULO A. Detalles para configurar el juego Cómo hemos usado un ordenador con sistema operativo ChromeOS, expliaremos las aplicaciones necesarias para arracar el juego en este sistema operativo. En la tabla tenemos las caracterı́sticas de este portátil.. Toshiba CB30 Chromebook Specifications • CPU: Haswell Celeron 2995U. 1.4GHz, dual-core, 2MB Cache • RAM: 2GB or 4GB DDR3 (Not upgradeable) • Display: 13.3” 1366x768 Disk: 16GB SSD (Not upgradeable) • HDMI port 2 x USB 3 SD slot (SDXC compatible) Headphone/mic combo jack Camera & mic Keyboard & touchpad Connectivity: WiFi: 802.11 a/b/g/n. A.0.1. Install Chromebrew (along with Ruby and Git). wget -q -O - https://raw.github.com/skycocker/chromebrew/master/install.sh | bash # necesario para instalar Node.js. A.0.2. Instalar Node.js. crew install node. A.0.3. Instalar socket.io. npm install socket.io. 39.

(54) 40. A.0.4. ANEXO A. DETALLES PARA CONFIGURAR EL JUEGO. Descargar el proyecto. git clone https://github.com/robinparadise/turtle vs buggers cd turtle vs buggers. A.0.5. Iniciar el juego en el servidor. node game.js # ahora el juego está escuchando en el puerto 5000 # desde un navegador ir a: http://localhost:5000.

(55)

Referencias

Documento similar

De hecho, este sometimiento periódico al voto, esta decisión periódica de los electores sobre la gestión ha sido uno de los componentes teóricos más interesantes de la

Ciaurriz quien, durante su primer arlo de estancia en Loyola 40 , catalogó sus fondos siguiendo la división previa a la que nos hemos referido; y si esta labor fue de

Para denegación hegeliana del mal: «Así como no existe lo fal- so, no existe el mal, es objetada primero por Sade y luego por la subjetividad romántica: en la mé- dula de la

De acuerdo con Harold Bloom en The Anxiety of Influence (1973), el Libro de buen amor reescribe (y modifica) el Pamphihis, pero el Pamphilus era también una reescritura y

Abstract: This paper reviews the dialogue and controversies between the paratexts of a corpus of collections of short novels –and romances– publi- shed from 1624 to 1637:

Por lo tanto, en base a su perfil de eficacia y seguridad, ofatumumab debe considerarse una alternativa de tratamiento para pacientes con EMRR o EMSP con enfermedad activa

The part I assessment is coordinated involving all MSCs and led by the RMS who prepares a draft assessment report, sends the request for information (RFI) with considerations,

o Si dispone en su establecimiento de alguna silla de ruedas Jazz S50 o 708D cuyo nº de serie figura en el anexo 1 de esta nota informativa, consulte la nota de aviso de la