Index du forum




Un petit coup de main... Vous pouvez nous aider à mettre ce site à jour: n'hésitez pas à me contacter !!!

* Connexion   * Inscription

* FAQ
Nous sommes actuellement le 29 Nov 2025, 18:00

Index du forum » Z80 Coding

Le fuseau horaire est UTC+1 heure


J'apprends l'assembleur : la memoire video

Modérateur: poulette73



Publier un nouveau sujet Répondre au sujet  Page 2 sur 2
 [ 20 message(s) ]  Aller vers la page Précédent  1, 2
  Aperçu avant impression Sujet précédent | Sujet suivant 
Auteur Message
JMD
 Sujet du message : Re: J'apprends l'assembleur : pbm 1 : les tableaux !
Message Publié : 18 Août 2010, 22:16 
Hors-ligne
Rulezzz
Rulezzz
Avatar de l’utilisateur

Inscription : 28 Déc 2007, 22:44
Message(s) : 295
Localisation : Toulouse
Hello,

Effectivement, en ne mettant que 199 lignes, mon petit bug disparait.

merci pour votre aide, j'ai atteint mon 1er objectif :)

La routine de Tatayoyode est rapide et compacte mais je ne peux pas réutiliser la fonction me donnant l'adresse de la ligne que j'ai principalement imaginé pour dessiner mon sprite.

Et vous comment auriez vous fait l'équivalent ?

Nb : j'ai trouvé cet article sur cpcrulez qui explique bien la mémoire vidéo

_________________
There is the theory of Möbius. A twist in the fabric of space where time becomes a loop


Haut
 Profil  
 
Longshot
 Sujet du message : Re: J'apprends l'assembleur : la memoire video
Message Publié : 19 Août 2010, 09:34 
Hors-ligne
VIP
VIP
Avatar de l’utilisateur

Inscription : 28 Août 2008, 23:41
Message(s) : 270
Effectivement, le chapitre optimisation viendra après.
Le coup du changement de ligne n'a pas forcément été évident pour chacun de nous la première fois :twisted:

Par contre, tu devrais retirer ta sauvegarde de sp, y compris le "call fin", qui ne servent à rien.
Car placé ainsi, cela dénote que tu ne maitrises pas encore bien la chose (si ta routine "init" avait été une sous sous routine, bouclage assuré via "fin").

Admettons que sp vaut &c000. Lorsque tu fais un "call init" tu mets sur la pile l'adresse de l'instruction suivant le "call init", soit l'adresse ou se trouve l'instruction "call EffaceEcran".
Dans "init", le registre sp vaut alors &C000-2 et c'est ce que tu mets dans le ld sp dans "fin". Lorsque tu fais un ret dans init, le registre sp revient à &C000.
Le "call fin" remet sp à &C000-2 et le ld sp,&C000-2 est donc inutile.


Haut
 Profil  
 
Longshot
 Sujet du message : Re: J'apprends l'assembleur : la memoire video
Message Publié : 19 Août 2010, 09:49 
Hors-ligne
VIP
VIP
Avatar de l’utilisateur

Inscription : 28 Août 2008, 23:41
Message(s) : 270
Citer :
Et vous comment auriez vous fait l'équivalent ?

Tout dépend si tu veux juste passer d'une ligne à l'autre ou calculer une adresse à partir de y, voire même de x (pour un sprite, je suppose que c'est ce que tu cherches)

Imagine que tu pré-calcules dans une table de 200x2 octets toutes les adresses de début de ligne (C000, C800, D000, D800, ...., C050, C850, ...) dans une table T.
Il te suffit pour trouver l'adresse de la ligne de lire [T+(yx2)]
Tu peux écrire ça en très peu de cycles.
Pour connaitre l'adresse en fonction de x, il suffit de diviser x par 2 en mode 0, 4 en mode 1 et 8 en mode 2, et d'additionner le résultat à l'adresse de la ligne.
Il ne te reste plus qu'à l'écrire :)


Haut
 Profil  
 
markerror
 Sujet du message : Re: J'apprends l'assembleur : la memoire video
Message Publié : 19 Août 2010, 11:21 
Hors-ligne
VIP
VIP

Inscription : 04 Sep 2007, 19:43
Message(s) : 739
Une petite version personnelle, qui garde l'esprit de ton source.
C'est normalement un peu plus rapide et plus court, que demande le peuple ?

On peut évidemment encore faire bien mieux, mais bon, le but, c'est plutôt de voir
qu'il n'y a pas une seule solution à un problème en assembleur.
J'ai viré tout ce qui touchait au SP, ça n'a aucun intérêt en fait dans ce type de
routine. Le SP ne doit être sauvegardé que si tu fais des manipulations de la pile
qui entreraient en conflit avec le système. Là, ce n'est pas le cas.

Bon, voici la bête :-).

ORG &8000
NOLIST ; pour Maxam

Ecran Equ &c000 ; definit l'adresse de l'ecran


;###### MAIN ######
Main
call Init ; sauvegarde tout ce qui doit l'etre et initialise les parametres
call EffaceEcran
ret ; bye bye

;###### Init ######
Init

XOR A ; mode 0
JP &BC0E ; definition du mode

;###### EffaceEcran ######
;###### colorie l'ecran en partant de la derniere ligne ######

; Ici, j'ai pas touche grand chose, il y a juste une petite amelioration
; en terme de vitesse. Le compteur de la boucle_EE_effC est divise par deux,
; car on efface toujours un nombre pair d'octets.
; Accessoirement, le premier octet efface est toujours pair, on peut donc se
; permettre de faire une incrementation de HL uniquement sur L (il ne debordera
; pas).

EffaceEcran
ld b,&CC ; la valeur a donner aux pixels
ld c,200 ; definit le nb de boucles (lignes)

Boucle_EE_effL
ld d,40 ; definit le nb de boucles (colonnes) divise par deux
ld a,c ; met dans a la ligne a chercher
push bc ; sauvegarde bc
push de ; sauvegarde de
call Calc_AddrLigne ; cherche l'adresse de la ligne dans HL
pop de ; recupere de
pop bc ; recupere bc

Boucle_EE_effC

ld (hl),b ; ecrit les 2 pixels
inc l ; position adressel ecran suivant
ld (hl),b ; ecrit les 2 pixels
inc hl ; position adresse ecran suivante

dec d ; decremente le nb de boucles (colonnes)
JP NZ,Boucle_EE_effC ; tant qu'on est pas a 0 , on recommance
dec c ; decremente le nb de boucles(lignes)
JP NZ,Boucle_EE_effL ; tant qu'on est pas a 0 , on recommance
ret



;###### Calc_AddrLigne ######
;###### Calcule l'adresse memoire de la ligne ######
;###### IN = a numero de ligne (en pixels) ######
;###### OUT = HL adresse memoire de la ligne ######

; Alors, cette version du calcul est un peu amelioree (moins d'instructions
; pour arriver au meme resultat :-).

; L'idee de base, c'est de se dire qu'il ne faut pas faire de calculs specifiques
; pour le nombre de lignes (0 a 7), car cette information est par defaut presente dans la
; valeur transmise, c'est le reste de la division par 8 du nombre total de lignes.
; On fait donc un simple AND &7 pour avoir ce nombre.

; Ensuite, une petite amelioration au niveau de rajout de la valeur &800 en fonction
; du nombre de lignes. Au lieu de faire une boucle, on fait un calcul, en fait, une
; simple multiplication par 8.

calc_addrligne

DEC A

LD E,A
AND &7
LD D,A ; on a dans D le nombre de lignes a (entre 0 et 7)

LD A,E
SRL A
SRL A
SRL A ; division de A par 8 = nombre de ligne caracteres

LD HL,ecran
AND A
JR Z,no_50

LD BC,&0050
cal_501
ADD HL,BC
DEC A
JR NZ,cal_501

no_50
LD A,D
ADD A,A
ADD A,A
ADD A,A ; on multiplie par 8
LD B,A
LD C,&0
ADD HL,BC
RET


Haut
 Profil  
 
tatayoyode
 Sujet du message : Re: J'apprends l'assembleur : pbm 1 : les tableaux !
Message Publié : 19 Août 2010, 11:31 
Hors-ligne

Inscription : 18 Août 2010, 16:56
Message(s) : 9
JMD a écrit :
La routine de Tatayoyode est rapide et compacte mais je ne peux pas réutiliser la fonction me donnant l'adresse de la ligne que j'ai principalement imaginé pour dessiner mon sprite. Et vous comment auriez vous fait l'équivalent ?


Salut,
Comme le souligne Markerror, utiliser les vecteurs systèmes (&bc29 et &bc26) qui calculent "tout cuit", ne nous apprennent effectivement pas grand chose sur la structure de la mémoire écran du cpc.
Je note cependant ta remarque qui comporte le mot "rapide" et forcément à un moment donné lorsque l'on veut aller plus loin, on y coupe pas !
Dans le cadre donc d'un calcul "rapide" d'une adresse écran à partir d'un numéro de ligne (y), l'option tables pré-calculées est, comme le dit Longshot, une solution redoutablement efficace...
Alternativement donc au dernier post de Markerror, je te propose ce petit bout de code qui calcul tout ça... à étudier, à adapter et à compléter à ta sauce... :

Code :
   org &8000
   nolist

   ld l,0                            ; 1ere ligne (-1 = 0)
   call calc_addrligne_fast   ; on lance le calcul
   ld (hl),&cc                    ; on affiche
   ret                              ; finito

;### calcul_addrligne_fast
;### in --> l=numero de ligne
;### out --> hl=adresse memoire de la ligne

calc_addrligne_fast
        ld h,&40   ; h=&40 et l=numero de ligne, sot si l=0, hl pointe en &4000 à savoir sur Table1
        ld a,(hl)   ; a=(hl) soit &00
        inc h       ; h=h+1 (cad h=&40+1 soit &41 et donc pointage sur Table2 en &4100)
        ld h,(hl)   ; h=(hl) soit &c0
        ld l,a       ; l=a soit l=&00
        ret          ; on a donc en sortie hl=&c000

        org &4000  ; table poids faibles adresses ecran en "y" assemblee en &40xx (h=&40 et xx=l=numero de ligne... )
Table1
   db &00   ; ligne1_faible
   db &00   ; ligne2_faible
   db &00   ; ligne3_faible
   db &00   ; ligne4_faible
   db &00   ; ligne5_faible
   db &00   ; ligne6_faible
   db &00   ; ligne7_faible
   db &00   ; ligne8_faible
   db &50   ; ligne9_faible
   db &50   ; ligne10_faible
;   ...etc... la table doit comprendre autant de db que tu as de lignes... tu peux d'ailleurs faire une routine qui genere cette table...

        org &4100  ; table poids forts adresses ecran en "y" assemblee en &41xx (h=&40+1 soit &41 et xx=l=numero de ligne...)
Table2
   db &c0   ; ligne1_fort
   db &c8   ; ligne2_fort
   db &d0   ; ligne3_fort
   db &d8   ; ligne4_fort
   db &e0   ; ligne5_fort
   db &e8   ; ligne6_fort
   db &f0   ; ligne7_fort
   db &f8   ; ligne8_fort
   db &c0   ; ligne9_fort
   db &c8   ; ligne10_fort
;   ...etc... la table doit comprendre autant de db que tu as de lignes... tu peux d'ailleurs faire une routine qui genere cette table...


Bon amusement...


Haut
 Profil  
 
Afficher les messages publiés depuis :  Trier par  
Publier un nouveau sujet Répondre au sujet  Page 2 sur 2
 [ 20 message(s) ]  Aller vers la page Précédent  1, 2

Index du forum » Z80 Coding

Le fuseau horaire est UTC+1 heure


Qui est en ligne ?

Utilisateur(s) parcourant ce forum : Aucun utilisateur inscrit et 27 invité(s)


Vous ne pouvez pas publier de nouveaux sujets dans ce forum
Vous ne pouvez pas répondre aux sujets dans ce forum
Vous ne pouvez pas éditer vos messages dans ce forum
Vous ne pouvez pas supprimer vos messages dans ce forum
Vous ne pouvez pas insérer de pièces jointes dans ce forum

Aller vers :  
Powered by phpBB® Forum Software © phpBB Group
Traduit en français par Maël Soucaze.