Ce modeste article s'adresse surtout aux débutants en GFA (hé oui, il en
reste encore !) ayant déjà quelques notions ainsi qu'à ceux qui sont
intéressés par la programmation de démos oldschool. Pour les nouveaux, un
scrolltext est tout simplement un texte qui défile en utilisant une fonte,
le plus souvent au format Degas. Je vous propose de programmer un
scrolltext horizontal avec une fonte en 16x16, le tout en 16 couleurs.
Avis aux graphistes
Avant d'entrer dans le vif du sujet, je voudrais m'adresser aux
graphistes qui dessinent des fontes. La plupart des fontes que j'ai vues
commencent par les 26 lettres de l'alphabet et finissent soit par les
chiffres, soit par la ponctuation. Il faut savoir qu'il est bien plus
pratique pour un codeur d'avoir les caractères de la fonte dans l'ordre des
caractères ASCII du ST. Cela va du caractère 32 (espace) au 91 (le Z si
je ne m'abuse). Ce qui donne ceci :
!"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ
N'oubliez pas qu'il y a le caractère "espace" juste avant le point
d'exclamation. Bien que certaines fontes ne comportent que des lettres,
le minimum vital est quand même d'avoir les lettres, les chiffres et un
minimum de ponctuation (point, virgule, tiret, point d'exclamation, point
d'interrogation, deux-points, les deux parenthèses et l'apostrophe). Si le
graphiste ne veut pas dessiner tous les caractères, il doit laisser un
blanc à la place.
Le principe
Avant de passer au source commenté, je vais vous expliquer en gros MA façon
de faire un scrolltext. Je sais bien que ce n'est pas LA meilleure
façon de procéder, mais elle marche et elle est assez rapide. Ça fait un
petit bout de temps que je programme en GFA et je n'ai jamais fait un seul
scrolltext. J'ai voulu faire un scrolltext qui se déplace par pas de 4
pixels, pour que ce ne soit ni trop lent, ni trop rapide. Chaque
caractère à afficher doit être coupé en tranches de 4 pixels de large.
Chaque tranche est affichée là où l'on veut que le scrolltext commence, et
puis on décale la partie de l'écran qui doit accueillir le scroll pour
afficher le morceau suivant. Et ainsi de suite. J'utilise l'écran physique
et l'écran logique (voir l'excellent article d'Exyl à ce sujet).
J'utilise l'instruction RC_COPY, qui est une instruction puissante en
GFA. Le mieux est encore d'utiliser BMOVE, mais il est moins pratique à
mettre en oeuvre. En revanche, évitez GET et PUT, ces instructions
prennent trop de temps machine.
Le listing du scrolltext
Vous devriez normalement retrouver le listing largement commenté, son
inline (la fonte) ainsi que la version compilée dans une archive
accompagnant le Toxic Mag.
' ' Scrolltext en 16x16 - aout/septembre 1999 ' Par The Beast/Typhoon pour le Toxic Mag 18 ' Fonctionne en ST basse ' RESERVE 5000 INLINE fonte%,7520
La fonte en question est bien une image Degas de 32 Ko mais je l'ai découpée
avec NeoChrome Master pour qu'elle prenne moins de place. Mine de rien,
j'ai économisé pratiquement 25 Ko. Si vous préférez utiliser l'image d'origine
de la fonte, voici ce qu'il aurait fallu mettre :
INLINE image%,32034 fonte%=image%+34 ~XBIOS(6,L:image%+2)La dernière ligne, c'est pour la palette de couleurs (voir plus loin). On continue :
@start DO @texte("[[[[[[[[[[[[[[[[[[[[[[[[ ATTENTION VOICI UN SCROLLTEXT QUI PARLE POUR RIEN DIRE ! ",320,100) LOOP UNTIL PEEK(&HFFFFFC02)=57 @fin
Notez que vous pouvez changer le texte ainsi que la position du scrolltext
(veillez à n'utiliser que des majuscules). Voilà pour la partie principale
du programme, il n'y a pas grand chose à rajouter. Voyons maintenant les
procédures...
La procedure "start"
PROCEDURE start old_phy%=XBIOS(2) old_log%=XBIOS(3) palette%=MALLOC(32) super%=GEMDOS(32,L:0) BMOVE &HFFFF8240,palette%,32
Ici, on stocke les adresses des écrans physique et logique pour les restituer
à la fin du programme. La palette est sauvegardée. A noter que tout le programme
tourne en superviseur.
ecran1%=MALLOC(32256) buffer1%=AND(ADD(ecran1%,256),&HFFFFFF00) ecran2%=MALLOC(32256) buffer2%=AND(ADD(ecran2%,256),&HFFFFFF00)
Là, c'est un peu particulier. Sachez que sur STF, la mémoire écran ne peut pas
être placée n'importe où, elle doit se trouver à une adresse multiple de 256.
Ce n'est pas le cas sur STE, ce qui permet d'avoir des scrollings plus
fins. La seconde ligne fait en sorte que la variable ecran1% pointe sur une
adresse multiple de 256. Je vous encourage vivement à faire ceci. Pour en
savoir plus, reportez-vous à l'article d'Exyl dans ce numéro.
~XBIOS(5,L:ecran2%,L:ecran1%,W:-1) CLS BMOVE ecran2%,ecran1%,32000
On déclare les deux écrans et on les nettoie à grand coup de CLS.
pal$=SPACE$(32) pal$=MKI$(&H0)+MKI$(&HF0F)+MKI$(&H577)+MKI$(&H467) +MKI$(&H356)+MKI$(&H245)+MKI$(&H134)+MKI$(&H23) +MKI$(&H12)+MKI$(&H464)+MKI$(&H353)+MKI$(&H242) +MKI$(&H131)+MKI$(&H20)+MKI$(&H10)+MKI$(&H677) ~XBIOS(6,L:V:pal$) RETURN
Là, on installe la palette. Cette dernière n'étant pas présente dans le
fichier INLINE, je l'ai rajoutée à la main. NeoChrome Master a aussi une
option pour sauver la palette sous forme de source assembleur, facilement
réutilisable en GFA.
Les procédures "texte" et "obtenir"
PROCEDURE texte(txt$,posx&,posy&) longueur%=LEN(txt$) FOR i&=1 TO longueur% ch&=ASC(MID$(txt$,i&,1)) @obtenir(ch&)
Après avoir calculé la longueur du texte, on recherche le code ASCII de
chaque caractère, l'un après l'autre, et l'on va demander à obtenir son
équivalent dans la fonte. Une autre méthode consiste à précalculer la place de
chaque caractère dans un tableau afin de gagner un peu de temps machine (je ne
l'ai pas fait car je ne suis pas sûr que cela économise tellement de temps
machine).
FOR j&=1 TO 4 RC_COPY fonte%,x&+(j&*4)-4,y&,4,15 TO ecran1%,posx&-4,posy&
Les lettres sont affichées par pas de 4 pixels. On coupe tous les caractères
par tranches de 4. Chaque caractère faisant 16 pixels de long, il faut
donc faire 4 découpages par caractère. Chaque bloc est ainsi affiché en bout
d'écran, prêt à être déplacé pour laisser la place au suivant.
IF PEEK(&HFFFFFC02)=56 CARD{&HFFFF8240}=&H404 ENDIF VSYNC CARD{&HFFFF8240}=&H0
Si l'on presse la touche ALTERNATE, la couleur du fond devient violette,
sinon elle reste noire. En gros, c'est une technique qui sert à visualiser le
temps machine occupé par la routine. A noter que CARD est bien plus rapide que
SETCOLOR.
RC_COPY ecran1%,4,posy&,posx&-4,15 TO ecran2%,0,posy& SWAP ecran1%,ecran2% ~XBIOS(5,L:ecran1%,L:ecran2%,W:-1)On déplace d'un cran (c'est-à-dire de 4 pixels) vers la gauche tous les caractères déjà affichés. Notez bien que la copie se fait dans le second écran. Il suffit ensuite de mettre un p'tit coup d'XBIOS 5 et le tour est joué ! Avec cette méthode, on ne peut utiliser qu'une fonte de 32x32 maximum ; car avec une fonte de 64x64 et plus, des bugs dans l'affichage graphique apparaissent. Il faudrait alors utiliser BMOVE, un peu plus compliqué à mettre en oeuvre.
NEXT j& EXIT IF PEEK(&HFFFFFC02)=57
Le scrolltext peut être interrompu en appuyant sur ESPACE.
NEXT i& RETURN PROCEDURE obtenir(ch&) IF ch&<=51 ! code ASCII inférieur ou égal à 51 x&=(ch&-32)*16 y&=0 ELSE IF ch&=>72 ! code ASCII supérieur ou égal à 72 x&=(ch&-72)*16 y&=32 ELSE ! code ASCII compris entre 50 et 71 x&=(ch&-52)*16 y&=16 ENDIF RETURN
Ces dernière lignes ont pour but de déterminer les coordonnées de chaque
caractère de la fonte. Les variables x& et y& vont ainsi indiquer à la routine
de scrolltext où trouver les caractères dont elle a besoin.
La procédure "fin"
PROCEDURE fin CLS ~XBIOS(5,L:old_log%,L:old_phy%,W:-1) BMOVE palette%,&HFFFF8240,32 ~GEMDOS(32,L:super%) ~MFREE(ecran2%) ~MFREE(ecran1%) ~MFREE(palette%) RESERVE EDIT RETURN
Cette sous-routine sert à rendre la main au système d'exploitation de la façon
la plus propre possible. Dans l'ordre : nettoyage de l'écran, restitution de
l'écran logique et de l'écran physique, remise en état de la palette et
nettoyage de la mémoire. Ne pas oublier non plus de se remettre en mode
utilisateur. Fini !
Les limites
J'ai essayé cette routine sur un Falcon et un STE. J'ai quand même remarqué
un truc très désagréable : si vous démarrez ce petit programme dans le
dossier AUTO depuis un STE (et peut-être depuis un STF aussi), ça rame ! Un
scrolltext en 16x16 va prendre presque 80% du temps machine, alors que
depuis le bureau GEM, il ne va en utiliser que 10% environ. A quoi est-ce
dû ? Je n'en suis pas sûr, mais je crois qu'il y a une histoire de blitter
derrière tout ça. Mais en revanche, ça passe nickel sur Falcon, que ce
soit en AUTO ou depuis le bureau.
Hasta la vista, baby !
J'en ai terminé pour cette fois. Si vous voulez améliorer les routines de
scrolltext, n'hésitez pas à me faire parvenir vos programmes compilés
ou bien, si vous êtes d'accord, vos sources (je les mettrai dans le
prochain Toxic, avec votre autorisation). Mais attention, pas de
routines en assembleur dans un INLINE ! Tout doit être fait en GFA ! Et pas
d'instructions du style CARD ou POKE pour déplacer le scrolltext, c'est
de la triche puisque ça équivaut à une instruction MOVE en assembleur !
8-)