Site

. Les News
. Le Forum
. L'équipe et les projets
. Les Tutoriaux
. IRC
. La boite à outils
. Les routines et algos indispensables
. Les liens


Les News de TI-FR







 

 



LES ECRANS VIRTUELS :




Rapide présentation :

Imaginons un cas simple, une flotte de sprites, une armée d'aliens dans leur soucoupe volante.... les aliens de Phoenix. Vous programmez ce jeu, et d'après votre algorithme vous allez deplacer la flotte ennemie. Vous n'avez jamais entendu parlé d'écrans virtuels mais vous savez afficher un sprite, vous allez donc calculer le positionnement futur de la flotte alien, effacer les sprites de leur ancienne position avec des petits carrés blancs et les rafficher : vous êtes content de vous, vous avez un petit scintillement d'étoile clignotante en plus du déplacement.... mais c'est pas très beau et ça nuit au gameplay...

Il existe donc une méthode bien plus simple (sans blague), rapide (largement plus rapide, vous verrez pourquoi), et plus serieuse d'afficher et d'effacer un sprite : les écrans virtuels.
Dans les grandes lignes, un ecran virtuel est une seconde mémoire vidéo sur laquelle on travaille EXACTEMENT comme dans l'ecran principal, on a donc deux écrans, pendant qu'on travail dans un écran on modifie l'autre....

interêt :

On affiche un ecran, on ne le modife pas, pendant ce temps, on efface le deuxième écran, on réaffiche les sprites qu'il faut aux endroits qu'il faut, puis on échange les deux écrans. C'est si rapide que l'oeil ne s'en rend pas compte, donc pas de clignotement... et on n'a pas effacé les sprites avec des petits carrés blancs mais effacé tout l'ecran, ce qui est bien plus rapide!!

Voici le diagramme :
nous avons deux écrans, #LCD_MEM (mémoire principale) et v_screen (l'ecran virtuel), par exemple.
 

J'efface lcd_mem (écran blanc)
\loop

J'efface v_screen

J'affiche les sprites dans v_screen

J'affiche v_screen dans lcd_mem, (c'est très rapide :)

bra \loop

Passons au codage :

les variables sont celles ci :

faut_pas_lutiliser         dc.w                 0
v_screen                     dc.l                   0             ;le pointeur de l'ecran virtuel

 

sprite        dc.l %11111111111111111111111111111111
                dc.l %10000000000000000000000000000001
  ; et ainsi de suite, le sprite doit faire 32 lignes dans cet exemple

N'oubliez pas : si vous utilisez Doors vous devez remplacer tous les tios:: par Doorsos:: !
 
 

création d'un ecran virtuel :
Un ecran virtuel est une seconde mémoire vidéo, il faut donc la créer, pour cela on utilise cette macro :
 

Création de l'ecran virtuel

newFakeScreen    macro
                            move.l           #3840,-(a7)                         ;taille en octet de l'ecran virtuel
                           jsr                 tios::HeapAllocThrow          ;fonction qui crée l'espace nécéssaire
                           lea                4(a7),a7

                            move.w        d0,faut_pas_lutiliser              ;ce truc ne servira que pour supprimer
                           tios::DEREF  d0,a0                                   ;le bloc mémoire
                            move.l           a0,v_screen                         ;ça, par contre, c'est le pointeur de l'ecran
                            endm

Commentaires :
    Vous ne devriez pas avoir besoin de comprendre cette macro, sachez juste que v_screen est le pointeur de l'écran virtuel et que c'est ce pointeur que vous aurez à utiliser dans le programme.

Bien sûr, après l'avoir créé il faut le supprimer :

eraseFakeScreen     macro
                              move.w     faut_pas_lutiliser,-(a7)

                              jsr             tios::HeapFree

                              lea            2(a7),a7

                              endm

Commentaires :
    Même remarque, vous aurez à supprimer l'écran virtuel après l'avoir créé, vous ne devriez pas non plus avoir à comprendre le fonctionnement.

Pour effacer l'ecran virtuel :

clearFakeScreen:
                            move.w     #959,d4

                            move.l       v_screen,a0

\loop

                            clr.l           (a0)+

                            dbra          d4,\loop

                            rts

Commentaires :
    Pourquoi #959 ?

    En tout la mémoire vidéo des TI89/92 fait
3840 octets, 30 octets par ligne, 128 lignes (sur TI89 les lignes 101 à 128 ne sont pas affichées, ansi que les 10octets du bout de la ligne.)
donc :

#30 * #128 = #3840

ce qui correspond à la taille des deux écrans.
Vous remarquerez le
"clr.l (a0)+" ce qui signifie qu'on supprime dans a0 long word par long word, or on a 3840 octets a supprimer => 3840/4 = 960
On utilise une boucle dbra, donc
960-1 = #959 (le compteur débute à 0 et fini à 959, donc 960 boucles, une de trop et la calculatrice plante)

    L'instruction dbra :
    Permet de faire une boucle for avec un pas de
#1, dans ce cas, l'instruction fait 960 boucles.

Juste pour le fun : une routine pour effacer l'ecran principal, cette routine
peut remplacer zap_screen de flib (fargo) et l'equivalent doors
 

cllcd:
                            move.w     #959,d4

                            move.l       #LCD_MEM,a0

\loop2

                            clr.l           (a0)+

                            dbra          d4,\loop2

                            rts

    Commentaires :
    Remplace
flib::zap_screen, et l'équivalent doors, toujours 960 boucles, le pointeur change, on efface plus v_screen, mais l'écran principal, dont le pointeur est #LCD_MEM (attention, dans ce cas il faut ajouter un "#" devant LCD_MEM, forcément écris en majuscule!
 

Maintenant que vous avez les macros pour créer, effacer et supprimer un écran virtuel vous savez les utiliser :)

Un exemple, reprenons l'ancien organigramme :
 

=======================================================================
J'efface #LCD_MEM (écran blanc)
=======================================================================

cllcd:
                            move.w     #959,d4

                            move.l       #LCD_MEM,a0

\loop2

                            clr.l           (a0)+

                            dbra          d4,\loop2

                            rts

=======================================================================
label de boucle
=======================================================================

\loop

=======================================================================
J'efface
v_screen
=======================================================================

clearFakeScreen:
                            move.w     #959,d4

                            move.l       v_screen,a0

\loop

                            clr.l           (a0)+

                            dbra          d4,\loop

                            rts

=======================================================================
J'affiche les sprites dans v_screen

=======================================================================

affSprite               macro
                            move.l         v_screen,a1        ;on charge le pointeur de l'écran virtuel dans a1

                            lea              sprite,a0              ;et le pointeur de sprite dans a0

                            move.w       #31,d7                ;32 boucles, on a un sprite qui fait 32 de haut

\bcl1:

                            move.l         (a0)+,(a1)           ;on copie le sprite dans a1

                            lea               30(a1),a1            ;retour à la ligne

                            dbra             d7,\bcl1

                            endm

    Commentaires :
    Cette routine permet d'afficher un sprite dans le coin supérieur gauche de l'écran, pour la routine complète lisez le tutorial

sur les sprites d'etan21!

    C'est une macro, c'aurait put être un sous programme comme une partie d'un programme... Mais n'oublions pas qu'un sous programme est forcément plus lent qu'une macro (lire Zguide) puisqu'insérée dans le prog pendant la compilation. Mais attention, si vous appelez plusieurs fois la macro vous aurez une duplication de label, vous aurez plusieurs \bcl1, donc une erreur à la compilation, pour l'évité voici ce que vous pouvez faire ;

    Appeler les différents sprites sprite1, sprite2, sprite3, etc. Ainsi pour l'appel de la macro vous aurez par exemple :

AffSprite 1

    Et dans la macro :

    lea        Sprite\1

\bcl\1:

    Et... plus de duplicate label name!

=======================================================================
J'affiche v_screen dans #LCD_MEM, (c'est très rapide :)
=======================================================================

copyFakeScreen:
                        move.l         #LCD_MEM,a0

                        move.l         v_screen,a1

                        move.l         #959,d0 ;toujours

\for

                        move.l         (a1)+,(a0)+

                        dbra             d0,\for

                        rts

    Commentaires :
    Vous remarquerez qu'on affiche pas a proprement parler l'ecran virtuel, mais on le copie dans
#LCD_MEM, la méthode est sensiblement la même que pour afficher un sprite, mais sans le retour à la ligne, puisque les deux écrans ont la même taille, c'est à dire 3840 octets!

=======================================================================
On ferme la boucle, retour au label \loop

=======================================================================

                        bra             \loop

    Commentaires :
    Boucle de branch sans condition, on préfère utiliser
bra plutôt que jmp !
 

    Si vous voulez voir les écrans virtuels en action, téléchargez les sources ET éxécutables pour TI89/92/92+ ici


GREATINGz :

Tutorial fait par la_fouine, le 26/02/2000,
dernier update :                le 04/03/2000

remerciements à :

Etan21 (il m'a tout appris ;)
krik (il joue du debugger comme John Wayne joue du colt...

ou l'homme qui debugge plus vite que son ombre )

Kox (Monsieur "près pour tes cours d'asm?" )



©Tous les programmes presents sur ce site sont soumis à l'autorisation de leur programmeurs respectifs pour toutes modifications. et dsistribution. La mise en page a necessité un certain travail, il serait donc plus correct de ne pas la plagier.