Actions en libgdx

Como ya os dije en el anterior post en libgdx nos da en la mayoria de casos una estructura para hacer un juego, pero algunas clases vamos a tener que implementarlas nosotros mismos, y cosas tan basicas como las acciones o los sprites parece que están a media (o esa impresión me da en un primer vistado) asi que lo primero que debemos hacer es comprender como está estructurada toda su filosofía y como hacer algo tan básico como mover un sprite con una acción para ir probando cosas

Empezamos por el package Scene2d en este paquete libgdx ofrece las clases básicas para hacer un juego en 2D, en principio nos vamos a centrar en estas 4 clases:

Stage es un contenedor para actores, podemos imaginar que será una pantalla de nuestro juego, no tiene porque ser de la dimensión de pantalla, puede ser mucho mas grande ya que controla la zona que se está viendo, permite hacer zoom o scrolls sobre ella. Recibe los eventos del touch y te dice sobre que actor de los que contiene se esta interactuando.

Actor es cualquier cosa de nuestro juego con la que podamos interactuar .. un sprite de toda la vida. Es una clase Abstracta, eso quiere decir que no la podemos instanciar, será obligatorio crear nuestra clase que implemente este método. Y será necesario implementar el método draw()

Group es una agrupación de Actors .. se usa para crear Sprites mas complejos que mantengan una jerarquía entre ellos

Action es la clase que se usa para aplicar cualquier transformación a un Actor,

libgdx incluye las siguientes acciones:

  • FadeIn – Modifica el alpha de un actor hasta llegar a 1.0f
  • FadeOut – Modifica el alpha de un actor hasta llegar a 0.0f
  • FadeTo – Modifica el alpha de un actor hasta llegar a un valor indicado
  • MoveBy – Desplaza un actor un valor determinado
  • MoveTo – Desplaza el actor hasta una posición
  • RotateBy – Rota el actor un ángulo especificado
  • RotateTo – Rota el actor hasta llegar a un ángulo
  • ScaleTo – Scala el actor a un factor indicado

Para combinar acciones nos ofrece estas 2 clases

  • Parallel – Ejecuta todas las acciones a la vez
  • Sequence – Ejecuta las acciones una por una

Otras acciones para combinar que no hacen ningún efecto por si solas

  • Repeat – Repite una acción las veces indicadas
  • Forever – Repite una acción para siempre
  • Delay – Hace una pausa de un tiempo antes de ejecutar la acción
  • Remove – Borra el actor de la Stage

Además de estas acciones todas implementan un Interpolator para modificar la velocidad o aceleración del movimiento, de esta forma se puede modificar el Rate de las acciones

  • AccelerateDecelerateInterpolator
  • AccelerateInterpolator
  • AnticipateInterpolator
  • DecelerateInterpolator
  • LinearInterpolator
  • OvershootInterpolator

En esta dirección podréis encontrar mucha mas info sobre estas clases, sobre acciones y sobre los Interpolators, aunque muy breve .. tampoco hay samples ni nada.
 2D-scenegraph implementation for 2D scenes

Actor and Actions

Empezamos por crear un Sprite muy basico que herede de Actor y vamos a ver como crear Actions sobre este objeto. Para ello creamos un proyecto para windows y vinculamos nuestras librerías de libgdx (se supone que ya sabéis como)

Nuestra clase Sprite de momento solo tiene un constructor que recibe como parámetro la textura que va a usar, e implementamos el método draw() que simplemente renderiza esa textura en su coordenada (le restamos la mitad de sus dimensiones para centrarlo sobre si mismo).

Esto podría ser nuestra implementación mínima de un Sprite, la clase Actor ya nos maneja su posición, su tamaño, su color, su alpha .. y todas esas cosas

Aquí tenéis el resultado en vídeo

Eventos tras la acción

Las acciones tienen un método setCompletionListener para asignarles una clase que herede de ‘OnActionCompleted’ he implemente el método completed(Action), este será el método que llama la acción cuando finalice. Java nos ofrece la facilidad de poner crear la clase dentro del método … que en general para procesos cortos como este será mas cómodo que implementar otra clase … en nuestro ejemplo vamos a hacer que el Sprite tire unas estrellitas cuando finalice su movimiento. la acción es idéntica a lo que teníamos antes, pero ahora añadimos el evento y en el ‘completed’ llamamos a un método para crear estrellas

Y aquí nuestro método buildStars() que simplemente crea 6 sprites de estrellitas y las pone en la misma posición para que se espandan. ya hemos visto como se crea la acción MoveTo. Ahora veremos como Crear una Secuencia de acciones y concatenaremos el MoveTo con un FadeOut y con un Remove .. que es una especie de acción comodín que simplemente destruye el Actor del Stage.

Como veis estamos añadiendo las estrellas a un stage2 … crear esta stage igual que teníamos la stage1 y ahora lo que hacemos en el Render es dibujar primero la stage2 que contiene las estrellas, y luego encima la stage con el sprite … de este modo podemos organizar los sprites por capas.

Y aquí el vídeo con el resultado

Android

Para crear el proyecto para android es suficiente con crear el lanzador, vincular el proyecto anterior y añadir todas las librerías necesarias

Aquí os dejo las
 Sample1-Android.apk Direct download (981.11 Kb)
 Sample1-Android.apk via barcode image

Aquí os dejo el proyecto para Eclipse
 libgdx-Sample1.zip (136.42 Kb)

Conclusión

En cocos2d fue mucho mas fácil …. y las acciones por lo menos estaban mas completas 🙁

Próximo punto …. Escenas y cambios de escenas

You may also like...

12 Responses

  1. JMM dice:

    Muy buen trabajo, gracias por compartir conocimientos, llevo un par de semanas viendo cosas de libgdx y de momento el tuyo ha sido el que más me ha ayudado a comprender la escena/actor. Al principio no me funcionó el ejemplo, añadiendo al método render de MyGame stage1.act(Gdx.graphics.getDeltaTime()); antes del draw corre al pelo, seguiré visitando el blog, un saludo

  2. neofar dice:

    Cuando hice esta clase todavía no tenia muy claro como funcionaban los actores. Si te fijas en la clase MySprite tengo el .act() dentro del Render() .. ese método es el que se encarga de dar ‘vida’ a la acción. Pero como tu comentas es mucho mejor llamar al .act() a nivel del Stage ya que este se encarga de llamar al correspondiente .act() de cada actor que contiene.

  3. Tlan3 dice:

    Hola, he leído tus tutoriales y me parecen muy buenos, pero me enfrento a un problema…. cuando compilo el proyecto de escritorio todo va de maravilla y se ejecuta sin problemas, pero al intentar ejecutarlo en Android truena la aplicación tanto en el emulador como en mi Optimus Black, ya lo escribí todo y también baje tu código pero no tengo resultados positivos.

    Espero me puedas ayudar

  4. snorforn dice:

    esta muy bueno el tutorial me corre de maravilla
    pero tengo una duda, como le meto una animacion a esto es, cuando apreto en la pantalla se mueva en esa direccion pero que cambie la imagen como simulando un personaje corriendo o volando

  5. neofar dice:

    aaaaamigo, que hoy queremos magia!!! … Pues en realidad es mas fácil de lo que parece pero hay que cambiar un poco las bases y conocer a fondo lo que libgdx hace por nosotros:

    En primer lugar yo estoy realizando todo a base de actores, la pega que tienen los actores es que están pensados para recibir eventos de touch. Que no es algo malo .. pero obviamente para un juego no puedes usar esta filosofía para todos los sprites.

    Libgdx tiene otras clases dentro de gdx.graphics.g2d.* y podrás ver que tienes una clase ‘Animation’, a esta clase le das un array de tus frames y el framerate que quieres y en cualquier momento le pides cual es el frame actual y el solito te lo calcula, ademas tiene sus opciones para indicar si la animación tiene loop y tal.

    Combinando esta clase con tu sprite te será muy fácil animar el bicho y hacer que ande palante, y hasta patrás.

    Por otro lado, estoy haciendo un juego y yo necesito tener una serie de sprites con su animación sincronizada, es decir que todos se estén siempre en el mismo frame a la vez (la clase Animation depende del tick, asi que puede que tengas varios sprites en la misma escena con un frame distinto). Así que al final he implementado yo el cambio de frame dentro de mi clase GdxSprite viene a ser tan sencillo como esto:

    copy and paste para que te hagas una idea

    y en el método draw()

    Como ves tengo un método para darle los frames, y luego otro método para indicar cual es el frame activo, de esta forma los sincronizo todos con el mismo evento externo que me gestiona la clase Director.

  6. snorforn dice:

    gracias amigo ya lo habia hecho analizando varias codigos lo que si no puedo hacer es los zoom de la camara como mencionas arriba o que una camara siga a un actor que ha salido de pantalla estoy analizando si este tema pero esta mas complicado que el otro

    muchas gracias si por el codigo te pasaste, disculpa si te pido otra ayudadita con lo que son las dimensiones del escenario los zoom y los scrool

  7. neofar dice:

    Eso ya es un tema bastante mas largo y que se sale de la temática de este post, así que tampoco me voy a enrollar, en los samples de libgdx tienes varios que te explican como hacerlo. Pero en resumen

    La clase Scene puede tener las dimensiones que quieras, mucho mas grandes que el área visible de la pantalla, y luego deberás crear una clase Camera que es mediante la cual controlas que área estas visualizando de esa Scene y que zoom, vamos que es lo que buscas

    Yo no creo por ahora que haga ningún post sobre esto, así que te va a tocar mirar los samples de libgdx

    😛

  8. snorforn dice:

    diculpa por las molestias, pero tengo una ultima consulta, como le coloco fondo a esto?

  9. neofar dice:

    Pues … un fondo no es mas que otra imagen, se pone igual que poner cualquier sprite, mírate el resto de ejemplos porque no tiene ningún misterio

  10. snorforn dice:

    disculpa que sea tan insistente pero he estado tratando meter la imagen pero no puedo, lo he intentado con:

    stage1.addActor(new GdxSprite(“data/start_screen.png” ,800/2,480/2));

    corre en java pero cuando quiero emularlo o traspasarlo a mi android se me cae, la imagen que pongo de fondo es potencia de 2 no se que pasa y te agredeceria mucho si es que me dices tambien como escalarla asi que ocupe toda el fondo, de antemano gracias

  11. snorforn dice:

    estaba probando el RotateTo y no me funciona, a ti te funciona? lo has probado? no se lo hago igual que el Moveto pero con rotate y no me sale te agradeceria mucho si me respondes

Deja un comentario

Tu dirección de correo electrónico no será publicada. Los campos necesarios están marcados *