Ya que el protipo empieza a funcionar le he buscado alguna vuelta de tuerca para que no sea un plataformas tradicional, para que tenga una jugabilidad especial. De momento he hecho que el jugador pueda controlar la dirección de la gravedad con unos nuevos botones:
El primero rota 45º y el segundo -45º. Además si arrastras de un botón de rotación hacia el otro rotas de golpe 180º.
La idea es diseñar los niveles de manera que solo se puedan superar usando adecuadamente los cambios de gravedad. Para limitar este superpoder habrá un número limitado de cambios disponibles que se pueden consultar en la parte inferior (G-Changes). Habrá que tomar decisiones de si vale la pena dar los 180 de golpe o ir por pasos, si hay que rotar en el aire, dar dos cambios seguidos de 180º para hacer una especie de salto largo...
El efecto físico que muestra el personaje cuando se cambia la gravedad es muy convincente y es bastante cómodo de controlar. Claro que al principio cuesta acostumbrarse a apretar izquierda para ir a la derecha cuando está boca abajo, pero ahí está parte de la gracia.
El problema ahora es que ha dejado de tener sentido diseñar las pantallas a base de bloques gordos. En la imagen de arriba se ve el personaje intentando andar en diagonal y el suelo le queda como un diente de sierra y no puede andar bien. Lo próximo tendrá que ser cambiar la creación del escenario y la gestión de las colisiones con el suelo y paredes para introducir unos mapas de este estilo suavizado:
Por tanto con este cambio deja de tener importancia el debate sobre si usar txt o png para guardar los mapas. Pero con suerte empezaremos otro: cómo debería almacenar la información para unos mapas redondeados como estos? Inicialmente voy a apostar por png optimizado. Este mapa concretamente tiene una resolución de 1000 por 700 px y ocupa unos 3kbytes. Otras opción podría ser usar algún formato vectorial, guardar líneas bezier con información de los vértices y curvaturas. Podría ser quizás el formato svg aunque he probado guardarlo y comprimir en zip y ocupa 1,7KB, que tampoco es tanto ahorro para los problemas que traería. Se aceptan sugerencias.
jueves, 16 de mayo de 2013
martes, 14 de mayo de 2013
Un cuento.
Había una vez un campesino chino, pobre pero sabio, que trabajaba la tierra duramente con su hijo.
Un día el hijo le dijo:
- ¡Padre, qué desgracia! ¡Se nos ha ido el caballo!
- ¿Porqué le llamas desgracia? – respondió el padre -Veremos lo que trae el tiempo…
A los pocos días el caballo regresó, acompañado de otro caballo.
- ¡Padre, qué suerte! – exclamó esta vez el muchacho -Nuestro caballo ha traído otro caballo.
- ¿Porqué le llamas suerte? – repuso el padre -Veamos qué nos trae el tiempo…
En unos cuantos días más, el muchacho quiso montar el caballo nuevo, y éste, no acostumbrado al jinete, se encabritó y lo arrojó al suelo. El muchacho se rompió una pierna…
- ¡Padre, qué desgracia! – exclamó ahora el muchacho -.¡Me he roto la pierna!
Y el padre, retomando su experiencia y sabiduría, sentenció:
- ¿Porqué le llamas desgracia? Veamos lo que trae el tiempo…
El muchacho no se convencía de la filosofía del padre, sino que gimoteaba en su cama.
Pocos días después pasaron por la aldea los enviados del rey, buscando jóvenes para llevárselos a la guerra.
Vinieron a la casa del anciano, pero como vieron al joven con su pierna entablillada, lo dejaron y siguieron de largo.
El joven comprendió entonces que nunca hay que dar ni la desgracia ni la fortuna como absolutas, sino que siempre hay que darle tiempo al tiempo, para ver si algo es malo o bueno.
Un día el hijo le dijo:
- ¡Padre, qué desgracia! ¡Se nos ha ido el caballo!
- ¿Porqué le llamas desgracia? – respondió el padre -Veremos lo que trae el tiempo…
A los pocos días el caballo regresó, acompañado de otro caballo.
- ¡Padre, qué suerte! – exclamó esta vez el muchacho -Nuestro caballo ha traído otro caballo.
- ¿Porqué le llamas suerte? – repuso el padre -Veamos qué nos trae el tiempo…
En unos cuantos días más, el muchacho quiso montar el caballo nuevo, y éste, no acostumbrado al jinete, se encabritó y lo arrojó al suelo. El muchacho se rompió una pierna…
- ¡Padre, qué desgracia! – exclamó ahora el muchacho -.¡Me he roto la pierna!
Y el padre, retomando su experiencia y sabiduría, sentenció:
- ¿Porqué le llamas desgracia? Veamos lo que trae el tiempo…
El muchacho no se convencía de la filosofía del padre, sino que gimoteaba en su cama.
Pocos días después pasaron por la aldea los enviados del rey, buscando jóvenes para llevárselos a la guerra.
Vinieron a la casa del anciano, pero como vieron al joven con su pierna entablillada, lo dejaron y siguieron de largo.
El joven comprendió entonces que nunca hay que dar ni la desgracia ni la fortuna como absolutas, sino que siempre hay que darle tiempo al tiempo, para ver si algo es malo o bueno.
viernes, 10 de mayo de 2013
Raspberry Pi
En la universidad hice un curso de RTOS y me pareció algo alucinante. Durante un tiempo fui siguiendo por encima las novedades que iban saliendo (básicamente, reducciones de tamaño). Incluso tenía un par de aplicaciones ideadas para jugar con la primera plaquita que me comprase. Pero por precio y falta de tiempo lo fui dejando hasta que lo olvidé por completo.
Hoy se ha presentado un compañero del curro con su nuevo juguete: una Raspberry Pi. Menudo descubrimiento. Mañana mismo me compro una!
No se si lo primero que haré será tunear algún coche teledirigido (o cualquier cosa que se mueva) para controlarlo con el mando de la wii
O si al final sólo la usaré como smartTV-TiVo casero
Pero las posibilidades son infinitas!
Hoy se ha presentado un compañero del curro con su nuevo juguete: una Raspberry Pi. Menudo descubrimiento. Mañana mismo me compro una!
No se si lo primero que haré será tunear algún coche teledirigido (o cualquier cosa que se mueva) para controlarlo con el mando de la wii
O si al final sólo la usaré como smartTV-TiVo casero
Pero las posibilidades son infinitas!
Etiquetas:
briconsejos,
curiosidades,
electrónica,
friki,
informatica,
linux
miércoles, 1 de mayo de 2013
Never End Peace And Love
Ayer me pasaron esta noticia y llevo un buen rato intentando completar la historia. Por ahora sólo he encontrado la versión de Simone Moro, y me parece bastante verosímil, por el historial de este tío y por cómo van algunas empresas de guías por las montañas. Eso sí, tal como cuidan el turismo en Nepal, me da que, con o sin razón, los tres guías/asistentes 'investigados' van a pillar.
Aquí la nota de prensa de Moro traducida: http://www.barrabes.com/actualidad/noticias/2-8412/graves-incidentes-everest-simone-moro.html
¿Quien dijo que entre alpinistas todo es camaradería?
Aquí la nota de prensa de Moro traducida: http://www.barrabes.com/actualidad/noticias/2-8412/graves-incidentes-everest-simone-moro.html
¿Quien dijo que entre alpinistas todo es camaradería?
martes, 30 de abril de 2013
Programando para Android - 3. El mapa
El colega kpacha me hace una pregunta muy interesante en el capítulo anterior y merece un mínimo análisis.
Me dice que eso de guardar el mapa en un archivo de imagen podría ocupar demasiado espacio comparado con almacenarlo en un archivo de texto plano, que tiene un byte por casilla y encima se puede comprimir.
Puede ser, porque el archivo de mapa de bits probablemente deberá tener al menos 3 bytes por cada píxel, uno para cada componente de color (RGB) otra para el canal alfa y vete a saber qué más y no podríamos aprovechar la compresión jpg porque necesitamos píxels "perfectos". Aunque sí podríamos usar compresiones tipo zip.
Para empezar aviso que en realidad la gracia de hacer el mapa con una imagen no es el espacio, es que se pueden "dibujar" las plataformas muy cómodamente con cualquier editor de imagen. Yo las he hecho con el Gimp y es escandalósamente rápido con la herramienta lápiz.
Pero sí es verdad que si se tratase de un juego con muchísimos mapas o que fuesen muy grandes podría empezar a notarse el espacio ahorrado. Así que he hecho uno de los mapas en txt a ver qué pasa.
Son 28 columnas y 15 filas. Aquí podéis ver los archivos que he hecho para comprobar el tamaño:
El excel lo he hecho para crear más rápido el de texto, pero está claro que no sale a cuenta, ocupa mucho más incluso comprimido. En formato csv comprimido mejora pero no alcanza a los otros.
El tamaño 1KB que marca es inexacto, hay que ir a propiedades de cada archivo o bien abrir nuestra querida consola de comandos:
Donde podemos ver que la cosa está más reñida de lo que parece.
map3.png es el archivo original que uso en el progama. Son 240 bytes sin hacer nada especial. No está nada mal y es mejor que el mapa.txt (450B) sin comprimir y mejor que el csv comprimido.
Entonces vemos que el mapatxt.zip es bastante mejor y que nos ahorra una buena proporción de espacio. Sería el momento de comprimir el png pero vemos que map3png.zip... ¡Ocupa más que sin comprimir! Lo cual nos da la idea de que el formato png lleva incorporadas compresiones lossless bastante buenas.
Entonces parece que ocupa menos el txt comprimido... pero hay algunas opciones en el formato png para ahorrar información en la cabecera del archivo. Si al guardar desactivamos todas estas opciones ganamos muchos bytes:
Así el archivo de 28x15 = 420 píxels se queda en 145 Bytes. Que ya está muy bien. Seguro que podríamos inventar algún formato para mejorar esos números, supongo que aún estamos lejos de la entropía mínima. Pero también habría que programar toda la lectura y análisis del archivo mientras que ahora es una única línea.
Incluso hay una opción para minimizar aún más el png, que sería usar color indexado. Si indicamos que solo va a haber un máximo de 8 colores se reduce la cantidad de bits por píxel y se consigue que ocupe 130B.
Además este minimapa tipo png se puede usar directamente dentro del juego para diferentes cosas como un "mapa en pantalla" superpuesto para que el jugador se ubique. También como previsualización en una hipotética pantalla de selección de niveles. Pero sobre todo pintar las plataformas con el ratón me ha convencido desde el principio.
Más cosas, he retocado el control de juego para hacerlo más estándar y he dibujado los controles en pantalla y las monedas. También he cambiado imágenes y el recorrido, los parámetros físicos del personajes y otros detalles...
Me dice que eso de guardar el mapa en un archivo de imagen podría ocupar demasiado espacio comparado con almacenarlo en un archivo de texto plano, que tiene un byte por casilla y encima se puede comprimir.
Puede ser, porque el archivo de mapa de bits probablemente deberá tener al menos 3 bytes por cada píxel, uno para cada componente de color (RGB) otra para el canal alfa y vete a saber qué más y no podríamos aprovechar la compresión jpg porque necesitamos píxels "perfectos". Aunque sí podríamos usar compresiones tipo zip.
Para empezar aviso que en realidad la gracia de hacer el mapa con una imagen no es el espacio, es que se pueden "dibujar" las plataformas muy cómodamente con cualquier editor de imagen. Yo las he hecho con el Gimp y es escandalósamente rápido con la herramienta lápiz.
Pero sí es verdad que si se tratase de un juego con muchísimos mapas o que fuesen muy grandes podría empezar a notarse el espacio ahorrado. Así que he hecho uno de los mapas en txt a ver qué pasa.
Son 28 columnas y 15 filas. Aquí podéis ver los archivos que he hecho para comprobar el tamaño:
El excel lo he hecho para crear más rápido el de texto, pero está claro que no sale a cuenta, ocupa mucho más incluso comprimido. En formato csv comprimido mejora pero no alcanza a los otros.
El tamaño 1KB que marca es inexacto, hay que ir a propiedades de cada archivo o bien abrir nuestra querida consola de comandos:
Donde podemos ver que la cosa está más reñida de lo que parece.
map3.png es el archivo original que uso en el progama. Son 240 bytes sin hacer nada especial. No está nada mal y es mejor que el mapa.txt (450B) sin comprimir y mejor que el csv comprimido.
Entonces vemos que el mapatxt.zip es bastante mejor y que nos ahorra una buena proporción de espacio. Sería el momento de comprimir el png pero vemos que map3png.zip... ¡Ocupa más que sin comprimir! Lo cual nos da la idea de que el formato png lleva incorporadas compresiones lossless bastante buenas.
Entonces parece que ocupa menos el txt comprimido... pero hay algunas opciones en el formato png para ahorrar información en la cabecera del archivo. Si al guardar desactivamos todas estas opciones ganamos muchos bytes:
Así el archivo de 28x15 = 420 píxels se queda en 145 Bytes. Que ya está muy bien. Seguro que podríamos inventar algún formato para mejorar esos números, supongo que aún estamos lejos de la entropía mínima. Pero también habría que programar toda la lectura y análisis del archivo mientras que ahora es una única línea.
Incluso hay una opción para minimizar aún más el png, que sería usar color indexado. Si indicamos que solo va a haber un máximo de 8 colores se reduce la cantidad de bits por píxel y se consigue que ocupe 130B.
Además este minimapa tipo png se puede usar directamente dentro del juego para diferentes cosas como un "mapa en pantalla" superpuesto para que el jugador se ubique. También como previsualización en una hipotética pantalla de selección de niveles. Pero sobre todo pintar las plataformas con el ratón me ha convencido desde el principio.
Más cosas, he retocado el control de juego para hacerlo más estándar y he dibujado los controles en pantalla y las monedas. También he cambiado imágenes y el recorrido, los parámetros físicos del personajes y otros detalles...
jueves, 25 de abril de 2013
Programando para Android - 2. En marcha
Ya tengo un primer prototipo muy esquemático con el funcionamiento básico.
Está organizado en dos pantallas usando las Screens del libgdx, una de bienvenida y después la del juego en sí. En punto de entrada carga la MainScreen que a su vez carga la GameScreen cuando se toca la pantalla.
En la GameScreen se carga un escenario de una manera que he visto por ahí y me ha parecido muy curiosa y muy útil. Se prepara previamente una imagen de mapa de puntos así:
Y luego el programa lee la imagen y según el color de cada píxel crea cada elemento en el lugar adecuado. Pero no crea el gráfico, solo el objeto. Todo queda flotando en el mundo de las ideas de Platón. Es lo que sería el Modelo en una arquitectura tipo MVC (Modelo-Vista-Controlador). Todas las operaciones, movimientos, interacción, lógica... se calcula en el modelo. Una vez esté preparado hay que renderizarlo, que es la función de la Vista, coger los elementos y representarlos en la pantalla. La idea sería esta:
El controlador en cambio lo he mezclado con el modelo así que es probable que tenga que reorganizar cosas. Aunque tampoco hay tanto que "controlar", no es tan grave.
La Vista (archivo WorldRenderer.java) se encarga de preparar la ventana de la aplicación, apuntar la cámara a la zona que nos interese, poner una imagen de fondo (está desactivado de momento) y representar cada elemento del juego con su imagen correspondiente en la posición adecuada. Aquí pongo un ejemplo en que se recorre toda la lista de bloques (paredes y suelo) y se dibuja una imagen en cada posición:
De momento solo sale el personaje y los bloques. La única interacción es conseguir que el personaje no pueda entrar en las paredes. Esto ha sido un poco lío pero al final parece que va bien. La estrategia es seguir estos pasos:
Queda muchísimo camino para que esto pueda ser llamado juego. Al menos el primer paso ya está hecho. Ahora hay que tomar decisiones sobre la jugabilidad, sobre el concepto, el arte, diseño de niveles, secciones, ayuda, música, animaciones, puntuación, vidas, marcador, optimización... y mil cosas más.
Quien quiera probarlo y modificarlo puede seguir los pasos del post anterior. Si solo queréis probarlo podéis ir a esta dirección desde un móvil android: Descargar juego NoWhereGame. Por supuesto lo hacéis bajo vuestra responsabilidad. Esta app puede derretir tu dispositivo y atropellar a tu gato.
El control del personaje de momento consiste en tocar la pantalla por abajo a la derecha o a la izquierda para ir en esa dirección y tocar por arriba para saltar. No se puede parar.
He estado a punto de poner aquí un pantallazo pero si no lo pongo es ligeramente más probable que lo instaléis.
Está organizado en dos pantallas usando las Screens del libgdx, una de bienvenida y después la del juego en sí. En punto de entrada carga la MainScreen que a su vez carga la GameScreen cuando se toca la pantalla.
En la GameScreen se carga un escenario de una manera que he visto por ahí y me ha parecido muy curiosa y muy útil. Se prepara previamente una imagen de mapa de puntos así:
Y luego el programa lee la imagen y según el color de cada píxel crea cada elemento en el lugar adecuado. Pero no crea el gráfico, solo el objeto. Todo queda flotando en el mundo de las ideas de Platón. Es lo que sería el Modelo en una arquitectura tipo MVC (Modelo-Vista-Controlador). Todas las operaciones, movimientos, interacción, lógica... se calcula en el modelo. Una vez esté preparado hay que renderizarlo, que es la función de la Vista, coger los elementos y representarlos en la pantalla. La idea sería esta:
El controlador en cambio lo he mezclado con el modelo así que es probable que tenga que reorganizar cosas. Aunque tampoco hay tanto que "controlar", no es tan grave.
La Vista (archivo WorldRenderer.java) se encarga de preparar la ventana de la aplicación, apuntar la cámara a la zona que nos interese, poner una imagen de fondo (está desactivado de momento) y representar cada elemento del juego con su imagen correspondiente en la posición adecuada. Aquí pongo un ejemplo en que se recorre toda la lista de bloques (paredes y suelo) y se dibuja una imagen en cada posición:
for(Block bl: world.blocks){
batch.draw(blockImage, bl.position.x-240, bl.position.y);
}
De momento solo sale el personaje y los bloques. La única interacción es conseguir que el personaje no pueda entrar en las paredes. Esto ha sido un poco lío pero al final parece que va bien. La estrategia es seguir estos pasos:
- Mover la componente x del personaje a las bravas.
- Comprobar si colisiona con algún bloque.
- Si colisiona retrocedemos un poco y volvemos al punto 2.
- Lo mismo con la componente y.
Queda muchísimo camino para que esto pueda ser llamado juego. Al menos el primer paso ya está hecho. Ahora hay que tomar decisiones sobre la jugabilidad, sobre el concepto, el arte, diseño de niveles, secciones, ayuda, música, animaciones, puntuación, vidas, marcador, optimización... y mil cosas más.
Quien quiera probarlo y modificarlo puede seguir los pasos del post anterior. Si solo queréis probarlo podéis ir a esta dirección desde un móvil android: Descargar juego NoWhereGame. Por supuesto lo hacéis bajo vuestra responsabilidad. Esta app puede derretir tu dispositivo y atropellar a tu gato.
El control del personaje de momento consiste en tocar la pantalla por abajo a la derecha o a la izquierda para ir en esa dirección y tocar por arriba para saltar. No se puede parar.
He estado a punto de poner aquí un pantallazo pero si no lo pongo es ligeramente más probable que lo instaléis.
miércoles, 17 de abril de 2013
Programando para android - 1. Inicio
Voy a iniciar otra serie (incluso sin haber acabado la del pedal, qué nivel) para poner en marcha un pequeño juego para android. La motivación es practicar un poco el java que lo tengo peor que oxidado. El hecho de ponerlo aquí en el blog me sirve para no dejarlo abandonado a la primera de cambio y para que os apuntéis los que estéis interesados en trastear un poco todo este tinglado.
He decidido usar una librería que parece interesante libgdx, sirve para facilitar un poco las cosas típicas de juegos como la gestión de los gráficos, la música, etc... y además se encarga de que el resultado sea compatible con pc, android, web y iphone. Para quien se apunte aquí está lo que hay que instalar previamente y aquí posteriormente.
Para iniciar el proyecto y preparar todos los archivos y dependencias viene un pequeño ejecutable (gdx-setup-ui.jar) que genera el esqueleto inicial:
Después voy a importarlos a Eclipse mediante Import => Existing project into workspace. Aquí ya podríamos empezar a picar pero si somos un poco elegantes preferiremos...
Ponerlo en sistema de control de versiones: He usado el subclipse para subirlo a code google goingnowhere. Ahí ya podéis ver el código inicial generado que es una especie de Hola mundo. Para verlo en funcionamiento hay que compilarlo en el Eclipse. Es muy útil lo de que se compile por igual en varias plataformas, no será necesario abrir un emulador de android ni conectar un dispositivo en modo debug porque simplemente podemos ejecutar la versión PC que es más directo y sabemos que luego funcionará también en las otras versiones.
Al ejecutar se muestra esto:
Una pantalla de inicio sencilla que muestra una imagen.
Si solo queréis probar (y colaborar) justo esta aplicación que he colgado los pasos se reducen y se simplifican:
He decidido usar una librería que parece interesante libgdx, sirve para facilitar un poco las cosas típicas de juegos como la gestión de los gráficos, la música, etc... y además se encarga de que el resultado sea compatible con pc, android, web y iphone. Para quien se apunte aquí está lo que hay que instalar previamente y aquí posteriormente.
Para iniciar el proyecto y preparar todos los archivos y dependencias viene un pequeño ejecutable (gdx-setup-ui.jar) que genera el esqueleto inicial:
Después voy a importarlos a Eclipse mediante Import => Existing project into workspace. Aquí ya podríamos empezar a picar pero si somos un poco elegantes preferiremos...
Ponerlo en sistema de control de versiones: He usado el subclipse para subirlo a code google goingnowhere. Ahí ya podéis ver el código inicial generado que es una especie de Hola mundo. Para verlo en funcionamiento hay que compilarlo en el Eclipse. Es muy útil lo de que se compile por igual en varias plataformas, no será necesario abrir un emulador de android ni conectar un dispositivo en modo debug porque simplemente podemos ejecutar la versión PC que es más directo y sabemos que luego funcionará también en las otras versiones.
Al ejecutar se muestra esto:
Una pantalla de inicio sencilla que muestra una imagen.
Si solo queréis probar (y colaborar) justo esta aplicación que he colgado los pasos se reducen y se simplifican:
- Instalar el JDK de Java.
- Instalar el ADT-Bundle de google (que lleva eclipse + un montón de cosas necesarias).
- Añadir el plugin subeclipse al Eclipse en Help => Install new software y en Work with ponemos la dirección http://subclipse.tigris.org/update_1.8.x e instalamos los paquetes que aparecerán.
- Importar mi proyecto mediante File => Import =>SVN => y ponemos la url https://goingnowhere.googlecode.com/svn/trunk
Etiquetas:
programación
Suscribirse a:
Entradas (Atom)











