mouse.c revision 53013
128328Ssos/*- 228328Ssos * Copyright (c) 1991-1997 S�ren Schmidt 328328Ssos * All rights reserved. 428328Ssos * 528328Ssos * Redistribution and use in source and binary forms, with or without 628328Ssos * modification, are permitted provided that the following conditions 728328Ssos * are met: 828328Ssos * 1. Redistributions of source code must retain the above copyright 928328Ssos * notice, this list of conditions and the following disclaimer 1028328Ssos * in this position and unchanged. 1128328Ssos * 2. Redistributions in binary form must reproduce the above copyright 1228328Ssos * notice, this list of conditions and the following disclaimer in the 1328328Ssos * documentation and/or other materials provided with the distribution. 1428328Ssos * 3. The name of the author may not be used to endorse or promote products 1528328Ssos * derived from this software withough specific prior written permission 1628328Ssos * 1728328Ssos * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 1828328Ssos * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 1928328Ssos * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 2028328Ssos * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 2128328Ssos * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 2228328Ssos * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 2328328Ssos * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 2428328Ssos * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 2528328Ssos * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 2628328Ssos * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 2728328Ssos * 2850476Speter * $FreeBSD: head/lib/libvgl/mouse.c 53013 1999-11-08 11:37:46Z yokota $ 2928328Ssos */ 3028328Ssos 3128328Ssos#include <stdio.h> 3228328Ssos#include <sys/types.h> 3328328Ssos#include <sys/ioctl.h> 3428328Ssos#include <sys/signal.h> 3528328Ssos#include <machine/console.h> 3628328Ssos#include "vgl.h" 3728328Ssos 3828328Ssos#define X 0xff 3928328Ssosstatic byte StdAndMask[MOUSE_IMG_SIZE*MOUSE_IMG_SIZE] = { 4028328Ssos X,X,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 4128328Ssos X,X,X,0,0,0,0,0,0,0,0,0,0,0,0,0, 4228328Ssos X,X,X,X,0,0,0,0,0,0,0,0,0,0,0,0, 4328328Ssos X,X,X,X,X,0,0,0,0,0,0,0,0,0,0,0, 4428328Ssos X,X,X,X,X,X,0,0,0,0,0,0,0,0,0,0, 4528328Ssos X,X,X,X,X,X,X,0,0,0,0,0,0,0,0,0, 4628328Ssos X,X,X,X,X,X,X,X,0,0,0,0,0,0,0,0, 4728328Ssos X,X,X,X,X,X,X,X,X,0,0,0,0,0,0,0, 4828328Ssos X,X,X,X,X,X,X,0,0,0,0,0,0,0,0,0, 4928328Ssos 0,0,0,X,X,X,X,0,0,0,0,0,0,0,0,0, 5028328Ssos 0,0,0,X,X,X,X,X,0,0,0,0,0,0,0,0, 5128328Ssos 0,0,0,0,X,X,X,X,0,0,0,0,0,0,0,0, 5228328Ssos 0,0,0,0,X,X,X,X,0,0,0,0,0,0,0,0, 5328328Ssos 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 5428328Ssos 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 5528328Ssos 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 5628328Ssos}; 5728328Ssosstatic byte StdOrMask[MOUSE_IMG_SIZE*MOUSE_IMG_SIZE] = { 5828328Ssos 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 5928328Ssos 0,X,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 6028328Ssos 0,X,X,0,0,0,0,0,0,0,0,0,0,0,0,0, 6128328Ssos 0,X,X,X,0,0,0,0,0,0,0,0,0,0,0,0, 6228328Ssos 0,X,X,X,X,0,0,0,0,0,0,0,0,0,0,0, 6328328Ssos 0,X,X,X,X,X,0,0,0,0,0,0,0,0,0,0, 6428328Ssos 0,X,X,X,X,X,X,0,0,0,0,0,0,0,0,0, 6528328Ssos 0,X,X,0,X,0,0,0,0,0,0,0,0,0,0,0, 6628328Ssos 0,0,0,0,X,X,0,0,0,0,0,0,0,0,0,0, 6728328Ssos 0,0,0,0,X,X,0,0,0,0,0,0,0,0,0,0, 6828328Ssos 0,0,0,0,0,X,X,0,0,0,0,0,0,0,0,0, 6928328Ssos 0,0,0,0,0,X,X,0,0,0,0,0,0,0,0,0, 7028328Ssos 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 7128328Ssos 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 7228328Ssos 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 7328328Ssos 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 7428328Ssos}; 7528328Ssos#undef X 7628328Ssosstatic VGLBitmap VGLMouseStdAndMask = 7753013Syokota VGLBITMAP_INITIALIZER(MEMBUF, MOUSE_IMG_SIZE, MOUSE_IMG_SIZE, StdAndMask); 7828328Ssosstatic VGLBitmap VGLMouseStdOrMask = 7953013Syokota VGLBITMAP_INITIALIZER(MEMBUF, MOUSE_IMG_SIZE, MOUSE_IMG_SIZE, StdOrMask); 8028328Ssosstatic VGLBitmap *VGLMouseAndMask, *VGLMouseOrMask; 8128328Ssosstatic byte map[MOUSE_IMG_SIZE*MOUSE_IMG_SIZE]; 8253013Syokotastatic VGLBitmap VGLMouseSave = 8353013Syokota VGLBITMAP_INITIALIZER(MEMBUF, MOUSE_IMG_SIZE, MOUSE_IMG_SIZE, map); 8428328Ssosstatic int VGLMouseVisible = 0; 8528328Ssosstatic int VGLMouseFrozen = 0; 8628328Ssosstatic int VGLMouseShown = 0; 8728328Ssosstatic int VGLMouseXpos = 0; 8828328Ssosstatic int VGLMouseYpos = 0; 8928328Ssosstatic int VGLMouseButtons = 0; 9028328Ssos 9128328Ssosvoid 9228328SsosVGLMousePointerShow() 9328328Ssos{ 9428328Ssos byte buf[MOUSE_IMG_SIZE*MOUSE_IMG_SIZE]; 9553013Syokota VGLBitmap buffer = 9653013Syokota VGLBITMAP_INITIALIZER(MEMBUF, MOUSE_IMG_SIZE, MOUSE_IMG_SIZE, buf); 9728328Ssos byte crtcidx, crtcval, gdcidx, gdcval; 9828328Ssos int pos; 9928328Ssos 10028328Ssos if (!VGLMouseVisible) { 10128328Ssos VGLMouseVisible = 1; 10228328Ssos crtcidx = inb(0x3c4); 10328328Ssos crtcval = inb(0x3c5); 10428328Ssos gdcidx = inb(0x3ce); 10528328Ssos gdcval = inb(0x3cf); 10628328Ssos __VGLBitmapCopy(VGLDisplay, VGLMouseXpos, VGLMouseYpos, 10728328Ssos &VGLMouseSave, 0, 0, MOUSE_IMG_SIZE, MOUSE_IMG_SIZE); 10828328Ssos bcopy(VGLMouseSave.Bitmap, buffer.Bitmap, MOUSE_IMG_SIZE*MOUSE_IMG_SIZE); 10928328Ssos for (pos = 0; pos < MOUSE_IMG_SIZE*MOUSE_IMG_SIZE; pos++) 11028328Ssos buffer.Bitmap[pos]=(buffer.Bitmap[pos]&~(VGLMouseAndMask->Bitmap[pos])) | 11128328Ssos VGLMouseOrMask->Bitmap[pos]; 11228328Ssos __VGLBitmapCopy(&buffer, 0, 0, VGLDisplay, 11328328Ssos VGLMouseXpos, VGLMouseYpos, MOUSE_IMG_SIZE, MOUSE_IMG_SIZE); 11428328Ssos outb(0x3c4, crtcidx); 11528328Ssos outb(0x3c5, crtcval); 11628328Ssos outb(0x3ce, gdcidx); 11728328Ssos outb(0x3cf, gdcval); 11828328Ssos } 11928328Ssos} 12028328Ssos 12128328Ssosvoid 12228328SsosVGLMousePointerHide() 12328328Ssos{ 12428328Ssos byte crtcidx, crtcval, gdcidx, gdcval; 12528328Ssos 12628328Ssos if (VGLMouseVisible) { 12728328Ssos VGLMouseVisible = 0; 12828328Ssos crtcidx = inb(0x3c4); 12928328Ssos crtcval = inb(0x3c5); 13028328Ssos gdcidx = inb(0x3ce); 13128328Ssos gdcval = inb(0x3cf); 13228328Ssos __VGLBitmapCopy(&VGLMouseSave, 0, 0, VGLDisplay, 13328328Ssos VGLMouseXpos, VGLMouseYpos, MOUSE_IMG_SIZE, MOUSE_IMG_SIZE); 13428328Ssos outb(0x3c4, crtcidx); 13528328Ssos outb(0x3c5, crtcval); 13628328Ssos outb(0x3ce, gdcidx); 13728328Ssos outb(0x3cf, gdcval); 13828328Ssos } 13928328Ssos} 14028328Ssos 14128328Ssosvoid 14228328SsosVGLMouseMode(int mode) 14328328Ssos{ 14428328Ssos if (mode == VGL_MOUSESHOW) { 14528328Ssos if (VGLMouseShown == VGL_MOUSEHIDE) { 14628328Ssos VGLMousePointerShow(); 14728328Ssos VGLMouseShown = VGL_MOUSESHOW; 14828328Ssos } 14928328Ssos } 15028328Ssos else { 15128328Ssos if (VGLMouseShown == VGL_MOUSESHOW) { 15228328Ssos VGLMousePointerHide(); 15328328Ssos VGLMouseShown = VGL_MOUSEHIDE; 15428328Ssos } 15528328Ssos } 15628328Ssos} 15728328Ssos 15828328Ssosvoid 15928328SsosVGLMouseAction(int dummy) 16028328Ssos{ 16128328Ssos struct mouse_info mouseinfo; 16228328Ssos 16328328Ssos if (VGLMouseFrozen) { 16428328Ssos VGLMouseFrozen++; 16528328Ssos return; 16628328Ssos } 16728328Ssos mouseinfo.operation = MOUSE_GETINFO; 16828328Ssos ioctl(0, CONS_MOUSECTL, &mouseinfo); 16928328Ssos if (VGLMouseShown == VGL_MOUSESHOW) 17028328Ssos VGLMousePointerHide(); 17128328Ssos VGLMouseXpos = mouseinfo.u.data.x; 17228328Ssos VGLMouseYpos = mouseinfo.u.data.y; 17328328Ssos VGLMouseButtons = mouseinfo.u.data.buttons; 17428328Ssos if (VGLMouseShown == VGL_MOUSESHOW) 17528328Ssos VGLMousePointerShow(); 17628328Ssos} 17728328Ssos 17828328Ssosvoid 17928328SsosVGLMouseSetImage(VGLBitmap *AndMask, VGLBitmap *OrMask) 18028328Ssos{ 18128328Ssos if (VGLMouseShown == VGL_MOUSESHOW) 18228328Ssos VGLMousePointerHide(); 18328328Ssos VGLMouseAndMask = AndMask; 18428328Ssos VGLMouseOrMask = OrMask; 18528328Ssos if (VGLMouseShown == VGL_MOUSESHOW) 18628328Ssos VGLMousePointerShow(); 18728328Ssos} 18828328Ssos 18928328Ssosvoid 19028328SsosVGLMouseSetStdImage() 19128328Ssos{ 19228328Ssos if (VGLMouseShown == VGL_MOUSESHOW) 19328328Ssos VGLMousePointerHide(); 19428328Ssos VGLMouseAndMask = &VGLMouseStdAndMask; 19528328Ssos VGLMouseOrMask = &VGLMouseStdOrMask; 19628328Ssos if (VGLMouseShown == VGL_MOUSESHOW) 19728328Ssos VGLMousePointerShow(); 19828328Ssos} 19928328Ssos 20028328Ssosint 20128328SsosVGLMouseInit(int mode) 20228328Ssos{ 20328328Ssos struct mouse_info mouseinfo; 20428328Ssos int error; 20528328Ssos 20628328Ssos VGLMouseSetStdImage(); 20728328Ssos mouseinfo.operation = MOUSE_MODE; 20828328Ssos mouseinfo.u.mode.signal = SIGUSR2; 20928328Ssos if ((error = ioctl(0, CONS_MOUSECTL, &mouseinfo))) 21028328Ssos return error; 21128328Ssos signal(SIGUSR2, VGLMouseAction); 21228328Ssos mouseinfo.operation = MOUSE_GETINFO; 21328328Ssos ioctl(0, CONS_MOUSECTL, &mouseinfo); 21428328Ssos VGLMouseXpos = mouseinfo.u.data.x; 21528328Ssos VGLMouseYpos = mouseinfo.u.data.y; 21628328Ssos VGLMouseButtons = mouseinfo.u.data.buttons; 21728328Ssos VGLMouseMode(mode); 21828328Ssos return 0; 21928328Ssos} 22028328Ssos 22128328Ssosint 22228328SsosVGLMouseStatus(int *x, int *y, char *buttons) 22328328Ssos{ 22428328Ssos signal(SIGUSR2, SIG_IGN); 22528328Ssos *x = VGLMouseXpos; 22628328Ssos *y = VGLMouseYpos; 22728328Ssos *buttons = VGLMouseButtons; 22828328Ssos signal(SIGUSR2, VGLMouseAction); 22928328Ssos return VGLMouseShown; 23028328Ssos} 23128328Ssos 23228328Ssosint 23328328SsosVGLMouseFreeze(int x, int y, int width, int hight, byte color) 23428328Ssos{ 23528328Ssos if (!VGLMouseFrozen) { 23628328Ssos VGLMouseFrozen = 1; 23728328Ssos if (width > 1 || hight > 1) { /* bitmap */ 23828328Ssos if (VGLMouseShown == 1) { 23928328Ssos int overlap; 24028328Ssos 24128328Ssos if (x > VGLMouseXpos) 24228328Ssos overlap = (VGLMouseXpos + MOUSE_IMG_SIZE) - x; 24328328Ssos else 24428328Ssos overlap = (x + width) - VGLMouseXpos; 24528328Ssos if (overlap > 0) { 24628328Ssos if (y > VGLMouseYpos) 24728328Ssos overlap = (VGLMouseYpos + MOUSE_IMG_SIZE) - y; 24828328Ssos else 24928328Ssos overlap = (y + hight) - VGLMouseYpos; 25028328Ssos if (overlap > 0) 25128328Ssos VGLMousePointerHide(); 25228328Ssos } 25328328Ssos } 25428328Ssos } 25528328Ssos else { /* bit */ 25628328Ssos if (VGLMouseShown && 25728328Ssos x >= VGLMouseXpos && x < VGLMouseXpos + MOUSE_IMG_SIZE && 25828328Ssos y >= VGLMouseYpos && y < VGLMouseYpos + MOUSE_IMG_SIZE) { 25928328Ssos VGLMouseSave.Bitmap[(y-VGLMouseYpos)*MOUSE_IMG_SIZE+(x-VGLMouseXpos)] = 26028328Ssos (color); 26128328Ssos if (VGLMouseAndMask->Bitmap 26228328Ssos [(y-VGLMouseYpos)*MOUSE_IMG_SIZE+(x-VGLMouseXpos)]) { 26328328Ssos return 1; 26428328Ssos } 26528328Ssos } 26628328Ssos } 26728328Ssos } 26828328Ssos return 0; 26928328Ssos} 27028328Ssos 27128328Ssosvoid 27228328SsosVGLMouseUnFreeze() 27328328Ssos{ 27428328Ssos if (VGLMouseFrozen > 1) { 27528328Ssos VGLMouseFrozen = 0; 27628328Ssos VGLMouseAction(0); 27728328Ssos } 27828328Ssos else { 27928328Ssos VGLMouseFrozen = 0; 28028328Ssos if (VGLMouseShown == VGL_MOUSESHOW && !VGLMouseVisible) 28128328Ssos VGLMousePointerShow(); 28228328Ssos } 28328328Ssos} 284