honzo@4gl.UUCP (04/11/87)
Some day's ago I asked the Net how the PC Mouse works. It happens to be quite simple... From: mcvax!masscomp!alang: ============================================================================ Serial mice normally run at 1200 baud. When the mouse is moved, or buttons are pressed or released, 5 bytes of information are sent. The first byte tells the current button state. The high order 5 bits are the pattern 10000 with the remaining 3 bits being the sate of the left, middle, and right mouse buttons. Bytes 2 and 3 are 8 bit signed values of delta x and delta y. Bytes 4 and 5 are also 8 bit signed values of delta x and delta y, relative to the previous two bytes. (ie. use both sets -- not just the first) I'm not sure, but since you know that the data is being sent at a constant rate, you might be able to infer the speed at which the mouse was being moved from the difference between the two sets of x and y. This information is for the mouse systems mouse, but this appears to have become a standard amongst serial mice. Alan Groupe ============================================================================ Thanks Alan! (and of course all the others not mentioned who send mail) ... which means that you can connect this (very cheap) mouse to any spare serial line! To try the above out, I decided to add a mouse to vi. It does not work perfect, but shows how you can use the mouse. This will compile on any Sys V machine. And run on an ANSI type terminal, provided that you map your keypad to the h j k l keys. Button 1 send's ESC. Button 2 sends . (again). Button 3 will start the context senzitive Pull Down Help function, but is not yet finished :-). (Could be done though, thinking about it, you only need to send a ^L to restore the Vi screen after you are done) When your are going to use mvi regularly, I suggest that you remove your bell from your terminal! (You'll find out why) Any comments etc are welcome at mcvax!4gl!honzo ------code follows ----- #! /bin/sh # This is a shell archive, meaning: # 1. Remove everything above the #! /bin/sh line. # 2. Save the resulting text in a file. # 3. Execute the file with /bin/[k]sh to create the files: # Makefile # mouse.c # mvi # This archive created: Sat Apr 11 02:03:41 1987 # By: honzo export PATH; PATH=/bin:$PATH if test -f 'Makefile' then echo shar: will not over-write existing file "'Makefile'" else cat > 'Makefile' << \S!H!A!R # all: mouse.do /dev/mouse mvi mouse.do: mouse.c cc mouse.c -o mouse.do /dev/mouse: /etc/mknod /dev/mouse p mvi: chmod +x mvi S!H!A!R fi # end of overwriting check if test -f 'mouse.c' then echo shar: will not over-write existing file "'mouse.c'" else cat > 'mouse.c' << \S!H!A!R /* mvi - Mouse vi, an example of using the PC Mouse This code will self-destroy when not used to make profit. Author: Honzo Svasek */ #include <stdio.h> #include <termio.h> #include <fcntl.h> int delta_x; /* movement in x direction (horizontal) */ int delta_y; /* movement in y direction (vertical) */ char but_1; /* button 1, 0 = up, 1 = down */ char but_2; /* button 2, 0 = up, 1 = down */ char but_3; /* button 3, 0 = up, 1 = down */ int fd; /* fd of mouse */ FILE *mouse, *o_mouse(); #define MOUSE_PORT "com1.d" main(argc, argv) int argc; char *argv[]; { char command[80]; int xnew=0, ynew=0, xold, yold; int i, c; if ((mouse = o_mouse(MOUSE_PORT)) == NULL) { perror(MOUSE_PORT); exit(-1); } for(;;) { r_mouse(mouse); if (but_1) { fputc('\033', stdout); } if (but_2) { fputc('.', stdout); fflush(stdout); fflush(mouse); } if (delta_y > 3) fputs("\033[B", stdout); if (delta_y < -3) fputs("\033[A", stdout); if (delta_x > 3) fputs("\033[C", stdout); if (delta_x < -3) fputs("\033[D", stdout); fflush(stdout); } } /* r_mouse - read a string of mouse data */ r_mouse(mouse) FILE *mouse; { char bn, x1, y1, x2, y2; while (!(bn = fgetc(mouse) & 0x80); x1 = fgetc(mouse); y1 = fgetc(mouse); x2 = fgetc(mouse); y2 = fgetc(mouse); delta_x = x1 > 128 ? x2 - x1 : x1 - x2; delta_y = y1 < 128 ? y2 - y1 : y1 - y2; but_1 = bn & 4 ? 0 : 1; but_2 = bn & 2 ? 0 : 1; but_3 = bn & 1 ? 0 : 1; return 0; } FILE *o_mouse(port) char *port; { char device[25]; struct termio tty; FILE *fdopen(); strcpy(device, "/dev/"); strcat(device, port); /* mouse-tty parameters */ tty.c_iflag = 0; tty.c_cflag = B1200 | CS8 | CREAD; tty.c_oflag = 0; tty.c_lflag = 0; tty.c_cc[4] = 5; tty.c_cc[5] = 5; if ((fd = open(device, O_RDONLY)) < 0) { perror(device); exit(-1); } ioctl(fd, TCSETA, &tty); return fdopen(fd, "r"); } S!H!A!R fi # end of overwriting check if test -f 'mvi' then echo shar: will not over-write existing file "'mvi'" else cat > 'mvi' << \S!H!A!R # mvi - vi with mouse - you must be drunk! if [ -p /dev/mouse -a -w /dev/mouse -a -r /dev/mouse ] then vi $* < /dev/mouse & mouse.do > /dev/mouse & cat -u > /dev/mouse kill -9 $! else echo "mvi: you must have a named pipe /dev/mouse" fi S!H!A!R chmod +x 'mvi' fi # end of overwriting check # End of shell archive exit 0 -- I_I( _ UUCP: ..mcvax!honzo@4gl I I ) Honzo Svasek @ 4GL Consultants b.v. FIDO: Honzo Svasek @ 500/333