Página 2 de 5

Re: Zx Spectrum: Cómo calcular el siguiente scanline en VRAM

Publicado: 11 Jul 2018, 19:34
por explorer
Bubu escribió:Bueno, de toas formas, si alguien coñoce algún código que resulte más eficiente o simétrico o más mejón, pos que lo diga (o calle para siempre :D )

Después de 30 años, todo este tipo de rutinas debería estar más que trillado y recogido en alguna base de datos, wiki y github.

Y si no está, un día nos moriremos y todo se perderá.

¿En el sitio del mundo del spectrum no tienen bibliotecas de estas rutinas?

Re: Zx Spectrum: Cómo calcular el siguiente scanline en VRAM

Publicado: 12 Jul 2018, 03:22
por Bubu
Yo no he sido capataz de encontrar una rutina de estas en toda intenné, pero evidentemente estar tié que estar, y habrán varias versiones, unas más optimizadas en espacio y otras en tiempo. Pero es que nu sé qué poner en el buscador pa encontrarlas. De toas formas como ya me fabriqué yo una y me va de lujo, no he insistido más.

Re: Zx Spectrum: Cómo calcular el siguiente scanline en VRAM

Publicado: 14 Jul 2018, 17:57
por explorer
He estado pensando un poco sobre este tema, y quizás se puede reducir un poco más.

No lo he probado. La idea es, simplemente, incrementar la dirección de VRAM conforme a las reglas de disposición de los bits.

Código: Seleccionar todo

calc_next_vram:
        ; Calcula la siguiente posición en VRAM del scanline inmediatamente inferior

        ; formato: hl = 010TTSSS RRRCCCCC
        ; IN  : hl = dirección en VRAM
        ; OUT : hl = dirección en VRAM siguiente
        ; modifica: registro a

        ; siguiente scanline
        inc h                   ; 010TTSSS++
        ld a, h                 ; 010TTSSS
        and %111                ; 00000SSS
        ret nz                  ; salir, aún no llegó a %000

                ld a, h                 ; 010TTSSS
                sub %00001000           ; TT--
                ld h, a                 ; ajustamos el desborde anterior

                ; siguiente fila
                ld a, l                 ; RRRC CCCC
                add %00100000           ; RRR++
                ld l, a
                ret nc

                        ; siguiente tercio
                        ld a, h                 ; 010TTSSS
                        add %00001000           ; TT++
                        ld h, a

                        ; aquí falta comprobar si a >= 0x58, que queda fuera de pantalla
                        ; pero no es necesario si sabemos que el gráfico no va a "escaparse" de la pantalla

                        ret

Si algo funciona, quizás se pueda mejorar.

Re: Zx Spectrum: Cómo calcular el siguiente scanline en VRAM

Publicado: 15 Jul 2018, 13:55
por Bubu
OK, procedo a catar. Muchas gracias, torpedo.

Re: Zx Spectrum: Cómo calcular el siguiente scanline en VRAM

Publicado: 15 Jul 2018, 19:28
por Bubu
Catado, y funciona perfestamente. Sólo se podría mejorar haciendo un ld e, h para volver luego a recuperar con ld h, e pero entóns sacribficamos un registro más, claro. Así que la veo divina de la muerte. Eso sí, el operador "ADD NN" no existe, jiji, sino que es "ADD A, NN"

De lujo, explorer, me quedo con tu rutina. Yo es que no controlo bien el acarreo con las operaciones arisméticas, y por eso en mi rutina utilizaba operaciones al bit.

Muchas gracias

Re: Zx Spectrum: Cómo calcular el siguiente scanline en VRAM

Publicado: 16 Jul 2018, 01:31
por explorer
Hola.

El sábado volví a entrar en los foros, y revisé mi mensaje otra vez. Lo vi "bien", pero mirándolo un poco "de lejos", noté algo extraño: "¿por qué estoy restando 1 a los bits de los tercios, y luego lo vuelvo a sumar si se trata del mismo caso?"

Esto es una sospecha de que quizás se puede hacer algo mejor.

Esta mañana, al despertarme, mi cerebro me tenía preparada una sorpresa: había encontrado la solución.

Ahora bien, como estaba medio dormido, era domingo, y no tenía nada que hacer, me volví a dormir, y cuando más tarde me levanté, ya ni me acordaba de este tema...

... hasta que he visto tus mensajes, esta noche, y me he acordado de que había encontrado otra solución, más corta y rápida.

Es casi la misma de antes, pero ahora nos ahorramos varios ciclos (los correspondientes a 3 instrucciones menos), algo fundamental en un rutina tan importante.

Código: Seleccionar todo

calc_next_vram:
        ; Calcula la siguiente posición en VRAM del scanline inmediatamente inferior

        ; formato de una dirección VRAM:
        ;     hl = 010TTSSS RRRCCCCC
        ;
        ;     TT : tercio de pantalla (0-3)
        ;    SSS : scanline dentro de la fila de carácter (0-7)
        ;    RRR : fila de carácter dentro del tercio (0-7)
        ;  CCCCC : columna (0-31)
        ;
        ; IN  : hl = dirección en VRAM
        ; OUT : hl = dirección en VRAM siguiente
        ;
        ; modifica:
        ;    registros: a, hl
        ;    flags: c, z

        ; siguiente scanline
        inc h                   ;  010TTSSS++
        ld a, h
        and %111                ; ¿00000SSS?

        ret nz                  ; salir, aún no llegó a %000

        ; aquí llegamos con SSS==0, y con TT (tercio) incrementado

        ; siguiente fila
        ld a, l                 ; RRRCCCCC
        add a, %00100000        ; RRR++
        ld l, a

        ; si hay acarreo, entonces deberíamos saltar al tercio siguiente,
        ; pero ya lo hicimos antes en el desborde de scanline,
        ; así que ya hemos terminado y salimos
        ret c

        ; pero si no, debemos mantenernos en el tercio anterior,
        ; por lo que debemos deshacer el incremento hecho antes

        ld a, h                 ; 010TTSSS
        sub %00001000           ; TT--
        ld h, a

        ret

Ya me dirás qué tal; no lo he probado.

Sobre el tema del operando add NN, eso depende del programa ensamblador que estés utilizando.

Por ejemplo, en este hilo: Adventures in ZX Spectrum Dev el ensamblador que está usando el autor (el sjasmplus) sí que lo admite.

Re: Zx Spectrum: Cómo calcular el siguiente scanline en VRAM

Publicado: 17 Jul 2018, 18:15
por Bubu
OK, he de catarlo, a ver si este fin de wikend activo mi frikismo, jiji.
Respecto a lo de ADD NN versus ADD A, NN, no te quiero quitar la razón, de hecho el estándar es ADD A, NN aunque a mí me gusta más ADD NN. Pero el estándar es el que es, y además he visto el compilador que mencionas, el SJASMPLUS, y en los ejemplos que trae usa siempre el estándar, uséase, ADD A, NN. La verdad es que en mis 35 años de pogramación en ensamblador nunca lo había visto como ADD NN, pero en fins, esto es lo de menos.

Y siguiendo para terminar con el tema esto de los estándares, antes usabas SUB NN lo cual está bien, y en tu última versión usas SUB A, NN, lo cual me dará error en el compilador cuando lo pruebe, en fins, es pa que veas que con ADD sí se pone el registro, y con SUB no. Esto no me parece lógico en el estándar, pero así es.

Re: Zx Spectrum: Cómo calcular el siguiente scanline en VRAM

Publicado: 17 Jul 2018, 23:49
por explorer
Pues sí, cierto. Es sorprendente que no exista el recíproco de ADD a,N como SUB a,N, debido a que existe la "extraña" combinación SUB a (restar a de a), que se usa para inicializar a o para poner el indicador Z a 1.

Bueno, lo he reeditado. Hace años que no programaba para Z80.

Re: Zx Spectrum: Cómo calcular el siguiente scanline en VRAM

Publicado: 18 Jul 2018, 00:52
por Bubu
Bueno, explorer, la rutina última ha sido catada y va de fábula, creo que ya más no se puede optimizar. De hecho es lo que yo quería saber si en intenné estaba la rutina al máximo de optizimización, que como decís todo está ya inventao, y estar tié que estar, pero yo no he tenido coxons de hallarla.

Lo dicho, ¡¡PERFECT!! Eres un montruo ;)

Re: Zx Spectrum: Cómo calcular el siguiente scanline en VRAM

Publicado: 20 Jul 2018, 17:34
por Uto
sjasm tiene un motón de macros incorporadas, para que los torpes no tengamos problemas. A mi me pasó una vez que puse LD HL, BC o algo así, y el tío me lo aceptó y cambió en el código a LD H, B / LD L, C. Lo malo es que me puse a depurar, y me puse a a hacer scroll en el depurador a ver donde estaba el trozo de código que yo quería, y precisamente mi ojo iba buscando el LD HL, BC, y claro no lo veía.

En fin, que en lugar de ayudarme me hizo la pascua, y además me resultó engañoso, porque yo andaba optimizando en memoria, y mi cabeza consideraba ese LD HL, BC como 1 byte, y eran 2.

Luego me estuve dando collejas a mi mismo un rato claro, por zoquete :-D