VDI et carte graphiques
ou la découverte de vq_scrninfo

En attendant qu'Osmose daigne se bouger les fesses pour m'envoyer les articles pour la mise en page (on a déjà une semaine de retard :(, je vous propose d'étudier une fonction bien intéressante que j'ai découverte dans la doc-dev de NVDI.
Rassurez-vous, NVDI n'est pas indispensable. Toutes les fonctions décrites dans cette doc-dev sont celles de la VDI, certaines sont propres à NVDI, d'autres sont les vieilles fonctions présentes depuis le TOS 1.0 .
La fonction que nous allons étudier est intermédiaire : elle ne nécessite pas NVDI, mais une upgrade du TOS, symbolisée par la présence du cookie "EdDI" dans la Cookie-Jar. Le Falcon la possède, ainsi que le Milan et autres nouvelles machines.

Et elle sert à quoi, cette fonction ?
Ben voilà : à connaître la struture de l'écran, c'est-à-dire comment les pixels sont organisés, combien de plans y a-t-il, si c'est au format Motorala (True Color du Videl) ou Intel (ATI de l'Eclispe ou S3 Virge du Milan), etc. De A à Z, la totale !

Donc pas besoin d'avoir à demander à l'utilisateur comment sont organisés les bits de ses pixels, ou d'avoir un fichier info (spécifique pour chaque carte graphique) avec chaque logiciel.
Ça change des PeuCeuh, non ?
Il suffit que le driver que vous avez mis dans votre dossier AUTO patche la fonction vq_scrninfo et vous ne vous occupez plus de rien. Et c'est le cas :) . vos logiciels, pour peu qu'ils aillent pêcher dans la fonction vq_scrninfo, afficheront vos zolies images sur, par exemple, l'Eclipse que vous avez installée dans votre bô Falcon.

Description de la fonction

J'ai (encore une fois) pompé sur la doc-dev de NVDI et commenté en bon frenchy.

Pour les amateurs du C, ça donne ça :
Déclaration (en C) : void vq_scrninfo( WORD handle, WORD *work_out );
Appel : vq_scrninfo( handle, work_out );
Pour les GFA-addicts :

    CONTRL(0)=102  ! code de vq_scrninfo
    CONTRL(1)=0    ! nombre d'entrées dans le tableau de points
    CONTRL(3)=1    ! nombre d'entrées dans le tableau des entiers
    CONTRL(5)=1    ! opcode (code complémentaire) de vq_scrninfo
    CONTRL(6)=handle& ! votre handle/identifiant VDI
    '
    INTIN(0)=2     ! code spécial
    '
    VDISYS         ! appel de la fonction

En retour, on obtient dans `CONTRL(4)->272`, c'est-à-dire 272 entiers dans le tableau de sortie `INTOUT`. Examinons tout ça.

Description des paramètres de retour

Pour les pro de C, remplacez INTOUT par work_out et divisez la valeur par 2.

Valeur | Intitulé | possibilités
`WORD{INTOUT}` | format des pixels | 0 : façon Atari, c'est-à-dire en plans enterlacés, regroupés mots par mots 1 : format standard (mode planar, 1 plan, puis l'autre, puis le suivant...) 2 : packed pixels (mode compressé, je connais pas) -1 : format inconnu ou pas accessible
`WORD{INTOUT+2}` | Présence d'une palette | 0 : pas de CLUT (mode monochrome du TTM194 ou SM124) 1 : CLUT géré par le hardware (mode traditionnel du Shifter en couleur) 2 : CLUT gérée en pseudo, par software (modes HiColor ou TrueColor)
`WORD{INTOUT+4}` | nombre de bitplanes | 1 à 32
`LONG{INTOUT+6}` | nombre de couleurs | 2 à 16 millions, si c'est 0, alors c'est supérieur à 16 millions
`WORD{INTOUT+10}` | largeur de la ligne en octets (?) | nécessite la version d'EdDI 1.1
`LONG{INTOUT+12}` | adresse de l'écran | nécessite la présence d'EdDI 1.1
`WORD{INTOUT+16}` | nombre de bits utilisés pour le rouge | utile en HiColor et TrueColor
`WORD{INTOUT+18}` | nombre de bits utilisés pour le vert | utile en HiColor et TrueColor
`WORD{INTOUT+20}` | nombre de bits utilisés pour le bleu | utile en HiColor et TrueColor
`WORD{INTOUT+22}` | nombre de bits utilisés pour la transparance | utile en TrueColor avec alpha-channel
`WORD{INTOUT+24}` | nombre de bits utilisés pour le genlock | Ah, ils ont même prévu de la digitalisation temps réel ?
`WORD{INTOUT+26}` | nombre de bits inutilisés | par exemple en HiColor 15 bits, il faut 16 bits (multiple de 8 obligatoire, dont 1 est inutilisé)
`WORD{INTOUT+28}` | ordre des bits | nécessite EdDI 1.1 g=vert, r=rouge, b-bleu, x=non utilisé, a=alpha-channel
Valeur | Commentaire
2 à 256 couleurs
0 | pas vraiment utile, ordre habituel
32768 couleurs
0 | ordre habituel : xrrrrrgg-gggbbbbb
1 | ordre particulier au Falcon : rrrrrggg-ggxbbbbb
7 | ordre inversé (Intel) : gggbbbbb-xrrrrrgg
65536 couleurs
0 | ordre habituel : rrrrrggg-gggbbbbb
7 | ordre inversé (Intel) : gggbbbbb-rrrrrggg
1677216 couleurs (24 bits)
0 | ordre habituel : rrrrrrrr-gggggggg-bbbbbbbb
7 | ordre inversé (Intel) : bbbbbbbb-gggggggg-rrrrrrrr
1677216 couleurs (32 bits)
0 | ordre habituel : aaaaaaaa-rrrrrrrr-gggggggg-bbbbbbbb
7 | ordre inversé (Intel) : bbbbbbbb-gggggggg-rrrrrrrr-aaaaaaaa
`WORD{INTOUT+32}` à `WORD{INTOUT+542}` | si on a une CLUT en hardware, c'est-à-dire `WORD{INTOUT+2}->1` | WORD{INTOUT+32} contient la valeur du pixel correspondant à la couleur 0 de la VDI WORD{INTOUT+34} contient la valeur du pixel correspondant à la couleur 1 de la VDI WORD{INTOUT+36} contient la valeur du pixel correspondant à la couleur 2 de la VDI ... WORD{INTOUT+542} contient la valeur du pixel correspondant à la couleur 255 de la VDI (*)
si on a une CLUT en software, c'est-à-dire un mode HiColor ou TrueColor et `WORD{INTOUT+2}=>2` | Si la valeur est -1 : alors le bit n'existe pas. WORD{INTOUT+32} contient la position (en bit) dans le pixel du bit 0 d'intensité rouge WORD{INTOUT+34} contient la position (en bit) dans le pixel du bit 1 d'intensité rouge ... WORD{INTOUT+64} contient la position (en bit) dans le pixel du bit 0 d'intensité vert WORD{INTOUT+66} contient la position (en bit) dans le pixel du bit 1 d'intensité vert ... WORD{INTOUT+96} contient la position (en bit) dans le pixel du bit 0 d'intensité bleu WORD{INTOUT+98} contient la position (en bit) dans le pixel du bit 1 d'intensité bleu ... WORD{INTOUT+128} contient la position (en bit) dans le pixel du bit 0 d'intensité alpha WORD{INTOUT+130} contient la position (en bit) dans le pixel du bit 1 d'intensité alpha .. WORD{INTOUT+160} contient la position (en bit) dans le pixel du bit 0 pour le genlock WORD{INTOUT+162} contient la position (en bit) dans le pixel du bit 1 pour le genlock ... WORD{INTOUT+192 à 254} sont des valeurs inutilisées WORD{INTOUT+256 à 452} sont réservées (0) (**)

(*) La valeur du pixel est, en mode CLUT hardware, une valeur déterminée par la superposition des bitplanes de l'image. En mode planar, c'est-à-dire standard, quand les plans sont distincts les uns des autres et non entrelacés, on prend le bit d'un point (x;y) du premier plan (il est égal à 1 ou 0), puis le bit aux même coordonnées du 2ème plan, et ainsi de suite.
La valeur du pixel est obtenue : le bit 0 du pixel correspond au bit du 1er plan, le bit 1 au bit du 2ème plan et ainsi de suite.

Les petits malins verront qu'on peut facilement convertir du 4 bit au 8 bits, c'est-à-dire de 16 en 256 couleurs : il suffit d'accoller 4 plans vierges aux 4 plans existant en mode planar/standard et faire un trans_form. Mieux, en accollant 1 plans vierge, puis 3 plans remplis de bits, on décale la valeur des pixels de 0 à 16 vers 234 à 249. Avec la table de conversion donnée plus haut (pixel<>VDI), on peut alors afficher une image 16 couleurs sans toucher aux couleurs des icônes (et à la couleur du pixel 255 qui est réservée).

(**) La valeur du pixel en mode CLUT software n'est pas relié à une palette de couleur. Le pixel EST la couleur. La correspondance pixel<>VDI n'est plus valable dans ce mode.
La fonction décrit alors l'organisation bit par bit des composantes rouge, vert, bleu (et alpha) des pixels. Par exemple en mode HiColor 15 bits du Falcon :

Bit 0 du niveau de rouge : `WORD{INTOUT+32}=11`
Bit 1 du niveau de rouge : `WORD{INTOUT+34}=12`
Bit 2 du niveau de rouge : `WORD{INTOUT+36}=13`
Bit 3 du niveau de rouge : `WORD{INTOUT+38}=14`
Bit 4 du niveau de rouge : `WORD{INTOUT+40}=15`
`WORD{INTOUT+42 à +62}=-1`
Bit 0 du niveau de vert : `WORD{INTOUT+64}=6`
Bit 1 du niveau de vert : `WORD{INTOUT+66}=7`
Bit 2 du niveau de vert : `WORD{INTOUT+68}=8`
Bit 3 du niveau de vert : `WORD{INTOUT+70}=9`
Bit 4 du niveau de vert : `WORD{INTOUT+72}=10`
`WORD{INTOUT+74 à +94}=-1`
Bit 0 du niveau de bleu : `WORD{INTOUT+96}=0`
Bit 1 du niveau de bleu : `WORD{INTOUT+98}=1`
Bit 2 du niveau de bleu : `WORD{INTOUT+100}=2`
Bit 3 du niveau de bleu : `WORD{INTOUT+102}=3`
Bit 4 du niveau de bleu : `WORD{INTOUT+104}=4`
`WORD{INTOUT+74 à +94}=-1`
pas d'alpha Channel donc `WORD{INTOUT+128 à +158}=-1`
il y a 1 bit pour le genlock, mais on ne s'occupe pas ici (en position 5).
Le reste jusqu'à `INTOUT+254` est égal à -1, l'autre partie est réservé.
On retrouve ainsi la structure rrrrrggg-ggxbbbbb ! Cela est plus simple avec la valeur de WORD{INTOUT+28} (ordre des bits), mais il se peut que votre EdDI soit à la version 1.0 est non 1.1 !
La version d'EdDI est retournée après appel à une fonction dont l'adresse est la valeur du cookie de "EdDI". Zyeutez la doc-dev de NVDI pour cela.

A la prochaine !

Pas trop dur ? parce qu'on verra les prochaines fois comment faire un jeu sous GEM, avec de la VDI toute propre et affichage d'images.

Rajah Lone
écrit le 22 Septembre 1999