/* vga test n°3 - gestion du curseur de souris - Patrick TRAU mai 02
Les commentaires dans les tests précédents ne sont pas tous recopiés ici !
ici j'affiche le curseur de la souris (une petite croix).
ce n'est pas facile : à chaque fois qu'on dessine le curseur, il faut sauver
le fond avant de dessiner. puis quand on veut l'effacer, il faut en fait
redessiner ce qu'on avait sauvegardé. Evidement, entre les 2 le fond (c.a.d le
dessin, sauf le curseur) ne doit pas être modifié sinon on redessine un
vieux fond non modifié.
Donc deux fonctions : cachecurs et montrecurs. Avant tout dessin on cache,
on dessine, puis on remontre (ça marche même si la souris a bougé pendant le
dessin). A tout moment (ou du moins pendant les phases où l'on attend un
mouvement de souris, les autres le curseur n'est pas obligatoire surtout
si elles sont courtes), il faut appeler montrecurs (je l'ai fait vérifier
si la souris a bougé, et dans ce cas il cache puis remontre)
*/
#include <stdio.h>
#include <stdlib.h>
#include <vga.h>
#include <vgamouse.h>
int choix_mode(void)
{
int m;
printf("choisissez une définition qui ne plante pas votre carte graphique:\n");
printf(" G320x200x16 1");
printf(" G640x200x16 2");
printf(" G640x350x16 3");
printf(" G640x480x16 4");
printf(" G320x200x256 5");
printf(" G320x240x256 6");
printf(" G320x400x256 7");
printf(" G360x480x256 8");
printf(" G640x480x2 9");
printf(" G640x480x256 10");
printf(" G800x600x256 11");
printf(" G1024x768x256 12 ? ");
scanf("%d",&m);
return m;
}
int choix_souris(void) // à faire avant vga_init car printf
{
int m;
printf("choisissez votre souris :\n");
printf(" MOUSE_MICROSOFT 0");
printf(" MOUSE_MOUSESYSTEMS 1");
printf(" MOUSE_MMSERIES 2");
printf(" MOUSE_LOGITECH 3");
printf(" MOUSE_BUSMOUSE 4");
printf(" MOUSE_PS2 5");
printf(" MOUSE_LOGIMAN 6");
printf(" MOUSE_GPM 7");
printf(" MOUSE_SPACEBALL 8");
printf(" MOUSE_NONE 9");
printf(" MOUSE_INTELLIMOUSE 10");
printf(" MOUSE_IMPS2 11 ? ");
scanf("%d",&m);
return m;
}
void tracecadre(void)
{
int x,y,coul,i;
x=vga_getxdim(); //récup résolution actuelle
y=vga_getydim();
// coul=vga_getcolors(); //récup nb de couleurs dans le mode actu
coul=vga_white(); //récup n° de couleur du blanc dans le mode actu
vga_drawline(0,0,x-1,0);
vga_drawline(x-1,0,x-1,y-1);
vga_drawline(x-1,y-1,0,y-1);
vga_drawline(0,y-1,0,0);
}
//partie spécifique souris, pourrait être compilée à part si nécessaire
// variables spécifiques à ma gestion du curseur. Elles DOIVENT être statiques
// car entre deux appels je dois récupérer le fond sauvé précédemment
#define TAILLECURS 5 /* en fait longueur d'une branche, taille totale = ça*2+1 */
#define coulcurs 14
static int cursvisible=0;
static int oldcursx=0;
static int oldcursy=0;
static int curssvg[(TAILLECURS*4)+1]={0};
void cachecurs(void)
// remet le fond tel qu'il était, où était le curseur (quelle que soit la pos actu)
{
int i,j,coulini;
vga_drawpixel(oldcursx,oldcursy); //rien que pour récupérer la couleur initiale, je dessine un pt que je teste après
coulini=vga_getpixel(oldcursx,oldcursy);
j=0;vga_setcolor(curssvg[j++]);vga_drawpixel(oldcursx,oldcursy); //réécriture du vieux fond
for(i=TAILLECURS;i;i--)
{vga_setcolor(curssvg[j++]);vga_drawpixel(oldcursx+i,oldcursy);
vga_setcolor(curssvg[j++]);vga_drawpixel(oldcursx-i,oldcursy);
vga_setcolor(curssvg[j++]);vga_drawpixel(oldcursx,oldcursy+i);
vga_setcolor(curssvg[j++]);vga_drawpixel(oldcursx,oldcursy-i);}
cursvisible=0;
vga_setcolor(coulini);
}
void montrecurs(void)
// lit la position de la souris et dessine le curseur ici, après avoir sauvé le fond
// si le curseur était déjà visible, à un autre endroit, je le cache et le mets à sa
// nouvelle place
{
int coulini;
int i,j;
mouse_update();
if(cursvisible) {if(oldcursx!=mouse_getx()||oldcursy!=mouse_gety())cachecurs();}
oldcursx=mouse_getx();oldcursy=mouse_gety(); //je sauve (écrase) la pos actu
j=0;curssvg[j++]=vga_getpixel(oldcursx,oldcursy); //curssvg du nouveau fond
for(i=TAILLECURS;i;i--)
{curssvg[j++]=vga_getpixel(oldcursx+i,oldcursy);
curssvg[j++]=vga_getpixel(oldcursx-i,oldcursy);
curssvg[j++]=vga_getpixel(oldcursx,oldcursy+i);
curssvg[j++]=vga_getpixel(oldcursx,oldcursy-i);}
vga_drawpixel(oldcursx,oldcursy); //rien que pour récupérer la couleur initiale, je dessine un pt que je teste après
coulini=vga_getpixel(oldcursx,oldcursy);
vga_setcolor(coulcurs);
vga_drawpixel(oldcursx,oldcursy); //tracé curseur
for(i=TAILLECURS;i;i--)
{ if(oldcursx+i<vga_getxdim())vga_drawpixel(oldcursx+i,oldcursy);
if(oldcursx-i>=0)vga_drawpixel(oldcursx-i,oldcursy);
if(oldcursy+i<vga_getydim())vga_drawpixel(oldcursx,oldcursy+i);
if(oldcursy-i>=0)vga_drawpixel(oldcursx,oldcursy-i); }
usleep(50); // pour que le cureur ne clignote pas, il faut rester un peu allumé, 50 mini, mais même 5000 ne ralentit pas trop
vga_setcolor(coulini);
cursvisible=1;
}
#define deplacecurs(a) montrecurs(a)
// avant, deplacecurs() cachait l'ancien curseur (car la souris avait bougé)
// et le montrait dans la nouvelle position. montrecurs de faut aussi (si cursvisible)
//fin partie spécifique
int main(void)
{
int i,mode,typesouris;
int mousetype,c,x,x0=0,y,y0=0;
//mode=5;
mode=choix_mode(); //4 @home, 4 à 12 à l'ipst
//typesouris=5;
typesouris=choix_souris(); //0 @home, 5 à l'ipst
//debut test graphique de base
vga_init();
vga_setmode(mode);
tracecadre();
vga_setcolor(14);
for(i=0;i<vga_getydim();i++) vga_drawpixel(i,i);
//debut test souris
mousetype=mouse_init("/dev/mouse",typesouris,400); //MOUSE_PS2 à l'ipst, MOUSE_MICROSOFT @home
mouse_setxrange( 0, vga_getxdim()-1);
mouse_setyrange( 0, vga_getydim()-1);
vga_setmousesupport(mousetype);
mouse_setscale(50);
montrecurs(); //par défaut le curseur était caché, puisque c'est moi qui le dessine
do
{
mouse_update(); // à faire à tout bout de champ pour que les fonctions suiv soient mises à jour
c=7&mouse_getbutton(); //0 pas de bouton, 4 gauche, 1 droite, 5 les 2 (2 boutons)
vga_setcolor(c*2);
x=mouse_getx();y=mouse_gety();
cachecurs();
if(c>0)vga_drawline(x0,y0,x,y); //tout tracé doit se faire curseur caché !
montrecurs();
x0=x;y0=y;
}
while(c<5); //sortie si appui sur les 2 boutons
fprintf(stderr,"sortie : %d\n",c);
//fin testsouris
vga_setmode(TEXT); //retourner au mode texte (important)
printf("fini\n"); //les printf se font sur la console où on a lancé la commande
return EXIT_SUCCESS;
}
Patrick Trau, IPST, Université Louis Pasteur Strasbourg, mai 2002