8BP: Ejemplo con lógicas masivas
Hola amigos de 8 Bits de Poder, en esta entrega semanal del curso de programación para amstrad CPC puedes ver un ejemplo con logicas masivas.
Tal como hablamos en los artículos anteriores, las lógicas masivas nos permiten mostrar un mayor numero de sprites en pantalla optimizando el uso de la memoria disponible, además de aprovechar eficientemente los ciclos de trabajo de nuestra CPU.
Pero espera… ¿Es posible que no sepas nada de 8 Bits de Poder? Puedes leer el primer artículo del curso de programación en Amstrad CPC de 8BP.
Ejemplo con logicas masivas
En el videojuego “Mutante Montoya”, los sprites enemigos se turnan para ejecutarse en los distintos ciclos del juego. Cuando programé este juego aun no había programado el mecanismo |ROUTEALL que permite asignar trayectorias fijas a los sprites, pero pude solventarlo con lógicas masivas.
En caso de quisieses hacer un juego donde los enemigos tuviesen “inteligencia”, no serviría una ruta fija, de modo que aunque tengamos el comando ROUTEALL, tendríamos que turnar la lógica de los sprites tal como se describe a continuación, por eso este ejemplo es interesante.
Supongamos que tenemos 3 soldados enemigos que se mueven de derecha a izquierda y de izquierda a derecha. Para ganar velocidad vamos a ejecutar sólo la lógica de un soldado en cada ciclo de juego.
Para que, a pesar de ello, la coordenada x de cada soldado siga avanzando, usaremos el flag de movimiento automático, en lugar de actualizarla nosotros.
Pega en tu emulador preferido y comprueba el funcionamiento de este código ejemplo con lógicas masivas:
10 MEMORY 23999 20 MODE 0: DEFINT A-Z: CALL &6B78:' install RSX 25 FOR j=0 TO 31:|SETUPSP,j,0,&X0:NEXT:'reset sprites 26 |SETLIMITS,0,80,0,200 30 'parametrizacion de 3 soldados 40 dim x(3):x%=0 50 x(1)=10:xmin(1)=10:xmax(1)=60: y(1)=60:direccion(1)=0:|SETUPSP,1,7,9 :|SETUPSP,1,0,&x1111: |SETUPSP,1,5,0: |SETUPSP,1,6,1 60 x(2)=20:xmin(1)=15:xmax(2)=40: y(2)=100:direccion(2)=1:|SETUPSP,2,7,10 :|SETUPSP,2,0,&x1111: |SETUPSP,2,5,0: |SETUPSP,2,6,-1 70 x(3)=30:xmin(1)=5:xmax(3)=50: y(3)=130:direccion(3)=0:|SETUPSP,3,7,9 :|SETUPSP,3,0,&x1111: |SETUPSP,3,5,0: |SETUPSP,3,6,1 80 for i=1 to 3:|LOCATESP,i,y(i),x(i):next: 'colocamos los sprites 81 i=0 89 '--- – BUCLE PRINCIPAL DEL JUEGO (CICLO DE JUEGO) – ------------ 90 i=i+1:gosub 100 92 if i=3 then i=0 93 |AUTOALL 94 |PRINTSPALL,1,0: ' anima e imprime los 3 soldados 95 goto 90 96 '------------ – FIN DEL CICLO DE JUEGO – ----------------------- 99 '--- – rutina de soldado – ----- 100 |PEEK,27003+i*16,@x%: x(i)=x% 101 IF direccion(i)=0 THEN IF x(i)>=xmax(i) THEN direccion(i)=1:|SETUPSP,i,7,10: |SETUPSP,i,6,-1 ELSE return 110 IF x(i)<=xmin(i) THEN direccion(i)=0:|SETUPSP,i,7,9 : |SETUPSP,i,6,1 120 return
Cada soldado tiene su propia lógica, pero solo ejecutamos una en cada ciclo de juego, aligerando muchísimo el ciclo de juego.
La única limitación es que al ejecutar la lógica de cada soldado una de cada 3 veces, la coordenada podría sobrepasar el límite que hemos establecido durante dos ciclos. Eso hace que debamos ser más cuidadosos al fijar el límite, asegurándonos al ejecutarlo que nunca invade y borra un muro de nuestro laberinto de pantalla, por ejemplo. Voy a tratar de explicar este problema con más precisión:
Supongamos que tenemos 8 sprites y nuestro sprite se mueve en todos los ciclos, pero sólo ejecutamos su lógica una de cada 8 veces. Imagínate un sprite que está en la posición x=20 y queremos que se mueva hasta la posición x=30 y dar la vuelta. Consideremos que el sprite tiene un movimiento automático con Vx=1. En ese caso comprobaremos su posición cuando x=20, x=28, x=36. ¡Al llegar a 36 nos daremos cuenta de que nos hemos pasado!!! y cambiaremos la velocidad del sprite a Vx=-1
Como ves el control de los límites de la trayectoria no es preciso, a menos que tengamos en cuenta esta circunstancia y fijemos el límite en algo que podamos controlar, que será Xfinal = Xinicial + n*8.
Esta limitación es minúscula si la comparamos con la ventaja de mover muchos sprites a gran velocidad. Con algo de astucia podemos incluso ejecutar la lógica menos veces, de modo que solo uno de cada dos ciclos se ejecute algún tipo de lógica de enemigos.
En nuestro próximo articulo hablaremos de como se realiza el movimiento en bloque de los sprites haciendo uso de las lógicas masivas.
Hasta aquí hemos llegado por hoy con el curso de programación en Amstrad CPC de 8 bits de poder Si tienes alguna duda puedes escribir en comentarios y te contestaré lo antes posible.
Todos los recursos, como manuales, ejemplos y juegos compilados de este curso los puedes encontrar en el repositorio Github de 8BP.
Hasta la semana que viene amigos 😄