Básicamente, en todos los juegos que he hecho hasta ahora, siempre tengo una variable como "current_state", que puede ser "game", "title screen", "gameoverscreen", etc.
Y luego, en mi función de actualización, tengo un enorme:
if current_state == "game"
game stuf
...
else if current_state == "titlescreen"
...
Sin embargo, no creo que esta sea una forma profesional / limpia de manejar estados. ¿Alguna idea sobre cómo hacer esto de una mejor manera? ¿O es esta la forma estándar?
lua
architecture
love2d
David Gomes
fuente
fuente
Respuestas:
Como estás hablando de pantallas, creo que es mejor separar toda esa lógica en diferentes pantallas. Lo que normalmente hago:
Defina una interfaz llamada pantalla y haga que varias pantallas la implementen. Como LoadingScreen, MainMenuScreen, GameScreen, GameOverScreen, HighScoreScreen, etc. En su juego, coloca una variable que contiene la pantalla actual. Cada ciclo, llama a screen.update () y renderiza la pantalla actual. Esto le ahorrará mucho "si este estado hace eso", ya que su estado se define en la pantalla actual.
Esto separará su lógica muy bien.
Código de ejemplo:
O dependiendo de la configuración de su juego, tal vez tenga un bucle infinito como juego.
fuente
Si ya está utilizando Middleclass, hay una excelente biblioteca de máquinas de estado para acompañarla llamada Statefull . Es fácil de usar y utiliza las mismas ideas que Matsemann propuso.
fuente
Si su
current_state
variable es una cadena, entonces esto es realmente fácil en Lua:fuente
Lo que hago es más o menos lo siguiente:
Tengo una estructura de datos de gráfico acíclico dirigida , que es esencialmente solo un grupo de nodos que apuntan entre sí. Cada nodo representa un sistema de juego. Por ejemplo, la interfaz de usuario, el mundo, la entrada, la representación. Y cada nodo apunta a otros nodos que vienen antes o después. Una vez que todos los nodos están en su lugar, es fácil aplanarlo en una lista simple. Configurar este DAG es lo primero que hago durante el inicio del juego. Cada vez que quiero agregar un nuevo sistema, digamos AI, solo puedo escribir ese código y luego decirle a mi juego de qué depende y qué debería depender de él.
Mi ciclo de juego principal viene después de eso y simplemente ejecuta cada sistema en orden. Primero se maneja la entrada, luego las actualizaciones mundiales, luego otras cosas ... La interfaz de usuario está cerca del final y la representación es la última. Cuando el juego comienza por primera vez, no hay mundo ni física ni IA, por lo que esos pasos se omiten esencialmente y solo se muestra la pantalla de título. Cuando comienzas el juego correctamente, la interfaz de usuario envía un mensaje al sistema mundial para que se encienda, y solo se ocupa de sí mismo. Administrar el estado del juego solo significa encender y apagar los diversos sistemas. Cada sistema tiene su propio conjunto de información de estado que se maneja más o menos independientemente de todos los demás (eso no es totalmentecierto en realidad, muchos sistemas actúan sobre el mismo conjunto de datos: el sistema UI, por ejemplo, toma datos del mundo para mostrar información, por ejemplo. El sistema de IA también necesita mirar y enviar mensajes a entidades en el mundo).
fuente
Así es como organizo mis estados en Lua + Love2d. Evita las largas declaraciones if / then.
Primero, creo una clase básica que contiene métodos de actualización (dt) y render (). También puede darle métodos de manejo de eventos, como onKeyDown (clave). Llamo a esta clase Etapa, pero cualquier objeto que implemente los métodos funcionará. Luego, hago una instancia de esa clase para cada estado del juego, implementando los métodos necesarios. Luego creo una tabla clave / valor con el nombre del estado y la instancia del estado. Luego, realice un seguimiento del estado actual en el ámbito global para que los estados puedan cambiarlo cuando se cumpla una determinada condición.
fuente
Bueno, aunque no es bonito, está bien manejar estados de esta manera, en mi opinión. Puede hacerlo mucho más limpio utilizando funciones para cada estado, como:
o algo más te molesta en este enfoque (quiero decir, excepto que el método de actualización es muy largo)?
fuente