home *** CD-ROM | disk | FTP | other *** search
/ Liren Large Software Subsidy 7 / 07.iso / c / c040 / 1.ddi / SAMPLES / MOUSE.C$ / MOUSE.bin
Encoding:
Text File  |  1990-03-06  |  9.4 KB  |  342 lines

  1. /* MOUSE - Module of mouse functions. To use it, include the MOUSE.H file
  2.  * in your program. The following functions are public:
  3.  *
  4.  *   MouseInit      - Initialize mouse
  5.  *   GetMouseEvent  - Get information about most recent mouse event
  6.  *   SetPtrVis      - Set visibility of pointer to HIDE or SHOW
  7.  *   SetPtrPos      - Set position of pointer
  8.  *   SetPtrShape    - Set shape of pointer in graphics modes, or
  9.  *                    character and color in text modes
  10.  *   GetPtrPos      - Get pointer position and button status
  11.  *
  12.  * The following structure is defined:
  13.  *
  14.  *   EVENT      -   Defines x, y, and mouse status of a mouse event
  15.  */
  16.  
  17. #include <graph.h>
  18. #include "mouse.h"
  19.  
  20. /* Internal information used by various mouse functions. */
  21. struct MOUINFO
  22. {
  23.     int      fExist, fInit, fGraph;
  24.     short    xVirtual,  yVirtual;
  25.     short    xActual,   yActual;
  26.     short    xLast,     yLast;
  27.     unsigned fsBtnLast, cBtn;
  28. } static mi =
  29. {
  30.     1, 0, 0,
  31.     0, 0,
  32.     0, 0,
  33.     0, 0,
  34.     0, 0
  35. };
  36.  
  37. /* MouseInit - Initialize mouse and turns on mouse pointer. Initializes
  38.  * all internal variables used by other mouse functions. This function
  39.  * should be called whenever a new video mode is set, since internal
  40.  * variables are mode-dependent.
  41.  *
  42.  * Params: none
  43.  *
  44.  * Return: 0 if no mouse available, otherwise number of buttons available
  45.  */
  46. int MouseInit()
  47. {
  48.     struct videoconfig vc;
  49.     char _far *pMode = (char _far *)0x00000449; /* Address for mode */
  50.  
  51.     /* Get video configuration. */
  52.     _getvideoconfig( &vc );
  53.  
  54.     /* Handle special case of Hercules graphics. To use mouse with video
  55.      * page 0. assume mode 6. To use mouse with page 1, assume mode 5.
  56.      * Since the mouse functions couldn't easily detect and adjust for
  57.      * page changes anyway, this code assumes page 0. Note also that the
  58.      * mouse for Hercules graphics must be set in text mono mode.
  59.      */
  60.     if( vc.mode == _HERCMONO )
  61.     {
  62.         _setvideomode( _TEXTMONO );
  63.         *pMode = 6;
  64.     }
  65.  
  66.     mi.fInit = 1;
  67.     _asm
  68.     {
  69.         sub     ax, ax              ; Mouse function 0, reset mouse
  70.         int     33h
  71.         mov     mi.fExist, ax       ; Set existence flag for future calls
  72.         or      ax, ax              ; If AX = 0, there is no mouse
  73.         jnz     exist
  74.         ret                         ;   so quit
  75. exist:
  76.         mov     mi.cBtn, bx         ; Save number of mouse buttons for return
  77.     }
  78.  
  79.     /* Set graphics flag. */
  80.     if( vc.numxpixels )
  81.     {
  82.         mi.fGraph = 1;
  83.         mi.yActual = vc.numypixels - 1;
  84.         mi.xActual = vc.numxpixels - 1;
  85.     }
  86.     else
  87.         mi.fGraph = 0;
  88.  
  89.     /* The mouse works on a virtual screen of 640 x pixels by (8 * textrows)
  90.      * vertical pixels. By default, it assumes 640 x 200 for 25-line mode.
  91.      * You must call function 8 to adjust for other screen sizes.
  92.      */
  93.     mi.xVirtual = 639;
  94.     if( mi.fGraph )
  95.         mi.yVirtual = vc.numypixels - 1;
  96.     else
  97.         mi.yVirtual = (vc.numtextrows << 3) - 1;
  98.  
  99.     /* Reset Hercules graphics mode and reset the height. */
  100.     if( vc.mode == _HERCMONO )
  101.     {
  102.         _setvideomode( _HERCMONO );
  103.         mi.xVirtual = 719;
  104.     }
  105.  
  106.     _asm
  107.     {
  108.         mov     ax, 8               ; Set minimum and maximum vertical
  109.         sub     cx, cx              ; Minimum is 0
  110.         mov     dx, mi.yVirtual     ; Maximum is 8 * rows (or rows SHL 3)
  111.         int     33h                 ; Adjust for 25, 30, 43, 50, or 60 lines
  112.  
  113.         mov     ax, 1               ; Turn on mouse pointer
  114.         int     33h
  115.  
  116.         mov     ax, 3               ; Get initial position and button status
  117.         int     33h
  118.         mov     mi.xLast, cx        ; Save internally
  119.         mov     mi.yLast, dx
  120.         mov     mi.fsBtnLast, bx
  121.     }
  122.     return mi.cBtn;                 /* Return the number of mouse buttons */
  123. }
  124.  
  125. /* GetMouseEvent - Check to see if there has been a mouse event. If event
  126.  * occurred, update event structure.
  127.  *
  128.  * Params: pEvent - Pointer to event structure
  129.  *
  130.  * Return: 1 if event, 0 if no event
  131.  */
  132. int GetMouseEvent( EVENT _far *pEvent )
  133. {
  134.     int rtn;
  135.  
  136.     /* Make sure that mouse is initialized and exists. */
  137.     if( !mi.fInit )
  138.         MouseInit();
  139.     if( !mi.fExist )
  140.         return 0;
  141.  
  142.     _asm
  143.     {
  144.         mov     ax, 3               ; Get Mouse position and button status
  145.         int     33h
  146.         sub     ax, ax              ; Assume no event
  147.  
  148.         cmp     cx, mi.xLast        ; Has column changed?
  149.         jne     event
  150.         cmp     dx, mi.yLast        ; Has row changed?
  151.         jne     event
  152.         cmp     bx, mi.fsBtnLast    ; Has button changed?
  153.         je      noevent
  154. event:
  155.         mov     ax, 1               ; If something changed, event occurred
  156.         mov     mi.xLast, cx        ; Update internal variables
  157.         mov     mi.yLast, dx
  158.         mov     mi.fsBtnLast, bx
  159. noevent:
  160.         mov     rtn, ax             ; Set return value
  161.     }
  162.  
  163.     /* If event, put adjust values in structure. */
  164.     if( rtn )
  165.     {
  166.         /* If graphics mode, adjust virtual mouse position to actual
  167.          * screen coordinates.
  168.          */
  169.         if( mi.fGraph )
  170.         {
  171.             pEvent->x = ((long)mi.xLast * mi.xActual) / mi.xVirtual;
  172.             pEvent->y = ((long)mi.yLast * mi.yActual) / mi.yVirtual;
  173.         }
  174.         /* If text mode, adjust virtual mouse position to 1-based
  175.          * row/column.
  176.          */
  177.         else
  178.         {
  179.             pEvent->x = (mi.xLast >> 3) + 1;
  180.             pEvent->y = (mi.yLast >> 3) + 1;
  181.         }
  182.         pEvent->fsBtn = mi.fsBtnLast;
  183.     }
  184.     return rtn;
  185. }
  186.  
  187. /* GetPtrPos - Get mouse pointer position and button status regardless of
  188.  * whether there was an event.
  189.  *
  190.  * Params: pEvent - Pointer to event structure
  191.  *
  192.  * Return: 0 if no mouse, otherwise 1
  193.  */
  194. int GetPtrPos( EVENT _far *pEvent )
  195. {
  196.     /* Make sure that mouse is initialized and exists. */
  197.     if( !mi.fInit )
  198.         MouseInit();
  199.     if( !mi.fExist )
  200.         return 0;
  201.  
  202.     _asm
  203.     {
  204.         mov     ax, 3               ; Get Mouse position and button status
  205.         int     33h
  206.         les     di, pEvent
  207.         mov     es:[di].x, cx
  208.         mov     es:[di].y, dx
  209.         mov     es:[di].fsBtn, bx
  210.     }
  211.  
  212.     /* If graphics mode, adjust virtual mouse position to actual
  213.      * screen coordinates.
  214.      */
  215.     if( mi.fGraph )
  216.     {
  217.         pEvent->x = ((long)pEvent->x * mi.xActual) / mi.xVirtual;
  218.         pEvent->y = ((long)pEvent->y * mi.yActual) / mi.yVirtual;
  219.     }
  220.     /* If text mode, adjust virtual mouse position to 1-based
  221.      * row/column.
  222.      */
  223.     else
  224.     {
  225.         pEvent->x >>= 3;
  226.         pEvent->y >>= 3;
  227.         pEvent->x++;
  228.         pEvent->y++;
  229.     }
  230.     return 1;
  231. }
  232.  
  233. /* SetPtrVis - Set pointer visibility.
  234.  *
  235.  * Params: state - SHOW or HIDE
  236.  *
  237.  * Return: 0 if no mouse, otherwise 1
  238.  */
  239. int SetPtrVis( enum PTRVIS pv )
  240. {
  241.     /* Make sure that mouse is initialized and exists. */
  242.     if( !mi.fInit )
  243.         MouseInit();
  244.     if( !mi.fExist )
  245.         return 0;
  246.  
  247.     _asm
  248.     {
  249.         mov ax, pv                  ; Show or hide mouse pointer
  250.         int 33h
  251.     }
  252. }
  253.  
  254. /* SetPtrPos - Set mouse pointer position.
  255.  *
  256.  * Params: x - column position in text modes, actual x coordinate in graphics
  257.  *         y - row position in text modes, actual y coordinate in graphics
  258.  *
  259.  * Return: 0 if no mouse, otherwise 1
  260.  */
  261. int SetPtrPos( short x, short y )
  262. {
  263.     /* Make sure that mouse is initialized and exists. */
  264.     if( !mi.fInit )
  265.         MouseInit();
  266.     if( !mi.fExist )
  267.         return 0;
  268.  
  269.     /* If graphics, adjust actual coordinates to virtual coordinates. */
  270.     if( mi.fGraph )
  271.     {
  272.         x = ((long)x * mi.xActual) / mi.xVirtual;
  273.         y = ((long)y * mi.yActual) / mi.yVirtual;
  274.     }
  275.     /* If text, adjust row/column to 0-based virtual coordinates. */
  276.     else
  277.     {
  278.         x--;
  279.         y--;
  280.         x <<= 3;
  281.         y <<= 3;
  282.     }
  283.  
  284.     _asm
  285.     {
  286.         mov     ax, 4               ; Set mouse position
  287.         mov     cx, x
  288.         mov     dx, y
  289.         int     33h
  290.     }
  291.     return 1;
  292. }
  293.  
  294. /* SetPtrShape - Set mouse pointer shape.
  295.  *
  296.  * Params: x - column position in text modes, actual x coordinate in graphics
  297.  *         y - row position in text modes, actual y coordinate in graphics
  298.  *
  299.  * Return: 0 if no mouse, otherwise 1
  300.  */
  301. int SetPtrShape( PTRSHAPE _far *ps )
  302. {
  303.     /* Make sure that mouse is initialized and exists. */
  304.     if( !mi.fInit )
  305.         MouseInit();
  306.     if( !mi.fExist )
  307.         return 0;
  308.  
  309.     /* If graphics, use pointer shape bitmask array. */
  310.     if( mi.fGraph )
  311.     {
  312.         _asm
  313.         {
  314.             les     di, ps
  315.             mov     bx, es:[di].g.xHot      ; Load hot spot offsets
  316.             mov     cx, es:[di].g.yHot
  317.             mov     dx, di
  318.             add     dx, 4
  319.  
  320.             mov     ax, 9                   ; Set graphics pointer
  321.             int     33h
  322.         }
  323.     }
  324.     /* If text, use pointer color/character values. */
  325.     else
  326.     {
  327.         _asm
  328.         {
  329.             les     di, ps
  330.             mov     bx, 0                   ; Use software cursor
  331.             mov     cl, es:[di].t.chScreen
  332.             mov     ch, es:[di].t.atScreen
  333.             mov     dl, es:[di].t.chCursor
  334.             mov     dh, es:[di].t.atCursor
  335.  
  336.             mov     ax, 10                  ; Set text pointer
  337.             int     33h
  338.         }
  339.     }
  340.     return 1;
  341. }
  342.