Asteroids: eliminación de zonas ocultas #Programación retro del Commodore 64

La nave ya puede acelerar, frenar, y girar bajo control. Si subimos muy arriba la nave aparece por abajo (y al revés). Y si vamos muy a la izquierda, la nave aparece por la derecha (y al revés). Esto es normal; el ciberespacio es así. Ahora estás aquí y luego estás allí.

Además, hay un trozo de pantalla a la derecha que no conseguimos alcanzar. Esto también es normal, puesto que los sprites utilizan nueve bits para su coordenada X, y de momento nosotros estamos usando sólo ocho. Todo lo que sea X>255 nos lo perdemos. Esto lo mejoraremos más adelante (librería "LibSprites").

Por último, tanto arriba, como abajo, como a la izquierda (y más adelante cuando metamos los nueve bits, también a la derecha), hay zonas de pantalla que están ocultas. Los sprites pueden meterse ahí y que no se vean. Esto estaría bien para esquivar los asteroides, si no fuera porque ellos también pueden circular por ahí si no tomamos ninguna medida.

Y esto es precisamente lo que vamos a hacer en esta entrada: eliminar las zonas ocultas.

Para ello, recurrimos a un truco. Temporalmente, vamos a poner el borde en blanco, de modo que se vea mejor la frontera de lo que queremos eliminar:

Asteroids - Borde blanco

Ya con el borde en blanco, vamos a jugar con la posición inicial de la nave, dando valores diferentes a las variables "posicionX" y "posicionY":

Asteroids - Jugar posicion inicial

Incluso si queremos ser muy precisos en la determinación de los límites, podemos cambiar a mano el "frame" inicial de la nave, de modo que usemos el frame 0 para el borde superior, el frame 4 para el borde inferior, y el frame 6 para el borde izquierdo:

Asteroids - Jugar frame inicial

De este modo, cambiando la posición y el frame iniciales, reensamblando y ejecutando, podemos determinar que los límites son:

  • Por la izquierda: Si jugadorX=1 el sprite todavía se ve; si jugadorX=0 el sprite ya no se ve.
  • Por la derecha: De momento esperamos, porque hay que mejorar el movimiento por la derecha.
  • Por arriba: Si jugadorY=30 el sprite todavía se ve; si jugadorY=29 el sprite ya no se ve.
  • Por abajo: Si jugadorY=249 el sprite todavía se ve; si jugadorY=250 el sprite ya no se ve.

Podemos tomarnos nuestro trabajo muy en serio, e implantar límites por arriba, abajo, izquierda y derecha. O también podemos observar que los límites más importantes son los verticales (Y), especialmente el de abajo, porque tiene un margen de 29 o 30 pixels que se tarda su tiempo en atravesar, y donde pueden ocultarse los sprites.

¿De verdad alguien piensa que una nave espacial, que viaja casi a la velocidad de la luz, tarda en atravesar un pixel (izquierda)? Los límites horizontales los podemos obviar, al menos de momento.

Y así nos disponemos a eliminar las zonas ocultas de arriba y abajo, cosa que logramos con este código nuevo en la rutina "actualizaPosicionJugador":

Asteroids - Zona oculta inferior

Es decir, la nueva coordenada X que nos devuelve la rutina "calculaNuevaPosicion" la aceptamos tal cual ("sta jugadorX"), y la nueva coordenada Y la sometemos a un tratamiento que consiste en:

  • Si la nueva Y es menor que 29, la convierte en 249.
  • Si la nueva Y es mayor que 250, la convierte en 30.

Es decir, si la nave acaba de entrar en la zona no visible de arriba (29), nos pasa a la zona visible de abajo (249). Y si la nave acaba de entrar en la zona no visible de abajo (250), nos pasa a la zona visible de arriba (30).

El tema de la comparación de números en ensamblador es más complejo de lo que parece, lo que me da pie para recordar esta tabla que resulta muy útil: (donde "A" es el acumulador y "M" es un valor inmediato o el contenido de una posición de memoria que se comparar con el acumulador mediante la instrucción "cmp"):

Condición Instrucción que salta
A = M beq
A <> M (distinto) bne
A > M bcs
A < M bcc
A >= M bcs
A <= M bcc o beq

Más adelante tendremos que mejorar el control de límites en dos sentidos:

  • Eliminar también las zonas ocultas horizontales, cuando ampliemos la coordenada X a nueve bits.
  • Encapsular este código en una nueva rutina independiente, o en dos rutinas (una para la X y otra para la Y), de modo que no se complique mucho la rutina "actualizaPosicionJugador".

Y ya podemos navegar por el ciberespacio sin zonas ocultas… Se pueden ver los cambios en el proyecto Asteroids04.


Editar

Josepzin

No hay comentarios:

Publicar un comentario