Subversion Repositories Kolibri OS

Rev

Go to most recent revision | Blame | Last modification | View Log | RSS feed

  1. /*
  2.     SDL - Simple DirectMedia Layer
  3.     Copyright (C) 1997, 1998, 1999, 2000, 2001  Sam Lantinga
  4.  
  5.     This library is free software; you can redistribute it and/or
  6.     modify it under the terms of the GNU Library General Public
  7.     License as published by the Free Software Foundation; either
  8.     version 2 of the License, or (at your option) any later version.
  9.  
  10.     This library is distributed in the hope that it will be useful,
  11.     but WITHOUT ANY WARRANTY; without even the implied warranty of
  12.     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  13.     Library General Public License for more details.
  14.  
  15.     You should have received a copy of the GNU Library General Public
  16.     License along with this library; if not, write to the Free
  17.     Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
  18.  
  19.     Sam Lantinga
  20.     slouken@devolution.com
  21. */
  22.  
  23.  
  24. /* General mouse handling code for SDL */
  25.  
  26. #include <stdio.h>
  27. #include <stdlib.h>
  28. #include <string.h>
  29.  
  30. #include "SDL_events.h"
  31. #include "SDL_events_c.h"
  32. #include "SDL_cursor_c.h"
  33. #include "SDL_sysvideo.h"
  34.  
  35.  
  36. /* These are static for our mouse handling code */
  37. static Sint16 SDL_MouseX = 0;
  38. static Sint16 SDL_MouseY = 0;
  39. static Sint16 SDL_DeltaX = 0;
  40. static Sint16 SDL_DeltaY = 0;
  41. static Uint8  SDL_ButtonState = 0;
  42.  
  43.  
  44. /* Public functions */
  45. int SDL_MouseInit(void)
  46. {
  47.         /* The mouse is at (0,0) */
  48.         SDL_MouseX = 0;
  49.         SDL_MouseY = 0;
  50.         SDL_DeltaX = 0;
  51.         SDL_DeltaY = 0;
  52.         SDL_ButtonState = 0;
  53.  
  54.         /* That's it! */
  55.         return(0);
  56. }
  57.  
  58. Uint8 SDL_GetMouseState (int *x, int *y)
  59. {
  60.         if ( x )
  61.                 *x = SDL_MouseX;
  62.         if ( y )
  63.                 *y = SDL_MouseY;
  64.         return(SDL_ButtonState);
  65. }
  66.  
  67. Uint8 SDL_GetRelativeMouseState (int *x, int *y)
  68. {
  69.         if ( x )
  70.                 *x = SDL_DeltaX;
  71.         if ( y )
  72.                 *y = SDL_DeltaY;
  73.         SDL_DeltaX = 0;
  74.         SDL_DeltaY = 0;
  75.         return(SDL_ButtonState);
  76. }
  77.  
  78. static void ClipOffset(Sint16 *x, Sint16 *y)
  79. {
  80.         /* This clips absolute mouse coordinates when the apparent
  81.            display surface is smaller than the real display surface.
  82.          */
  83.         if ( SDL_VideoSurface->offset ) {
  84.                 *y -= SDL_VideoSurface->offset/SDL_VideoSurface->pitch;
  85.                 *x -= (SDL_VideoSurface->offset%SDL_VideoSurface->pitch)/
  86.                                 SDL_VideoSurface->format->BytesPerPixel;
  87.         }
  88. }
  89.  
  90. /* These are global for SDL_eventloop.c */
  91. int SDL_PrivateMouseMotion(Uint8 buttonstate, int relative, Sint16 x, Sint16 y)
  92. {
  93.         int posted;
  94.         Uint16 X, Y;
  95.         Sint16 Xrel;
  96.         Sint16 Yrel;
  97.  
  98.         /* Don't handle mouse motion if there's no cursor surface */
  99.         if ( SDL_VideoSurface == NULL ) {
  100.                 return(0);
  101.         }
  102.  
  103.         /* Default buttonstate is the current one */
  104.         if ( ! buttonstate ) {
  105.                 buttonstate = SDL_ButtonState;
  106.         }
  107.  
  108.         Xrel = x;
  109.         Yrel = y;
  110.         if ( relative ) {
  111.                 /* Push the cursor around */
  112.                 x = (SDL_MouseX+x);
  113.                 y = (SDL_MouseY+y);
  114.         } else {
  115.                 /* Do we need to clip {x,y} ? */
  116.                 ClipOffset(&x, &y);
  117.         }
  118.  
  119.         /* Mouse coordinates range from 0 - width-1 and 0 - height-1 */
  120.         if ( x < 0 )
  121.                 X = 0;
  122.         else
  123.         if ( x >= SDL_VideoSurface->w )
  124.                 X = SDL_VideoSurface->w-1;
  125.         else
  126.                 X = (Uint16)x;
  127.  
  128.         if ( y < 0 )
  129.                 Y = 0;
  130.         else
  131.         if ( y >= SDL_VideoSurface->h )
  132.                 Y = SDL_VideoSurface->h-1;
  133.         else
  134.                 Y = (Uint16)y;
  135.  
  136.         /* If not relative mode, generate relative motion from clamped X/Y.
  137.            This prevents lots of extraneous large delta relative motion when
  138.            the screen is windowed mode and the mouse is outside the window.
  139.         */
  140.         if ( ! relative ) {
  141.                 Xrel = X-SDL_MouseX;
  142.                 Yrel = Y-SDL_MouseY;
  143.         }
  144.  
  145.         /* Update internal mouse state */
  146.         SDL_ButtonState = buttonstate;
  147.         SDL_MouseX = X;
  148.         SDL_MouseY = Y;
  149.         SDL_DeltaX += Xrel;
  150.         SDL_DeltaY += Yrel;
  151.         SDL_MoveCursor(SDL_MouseX, SDL_MouseY);
  152.  
  153.         /* Post the event, if desired */
  154.         posted = 0;
  155.         if ( SDL_ProcessEvents[SDL_MOUSEMOTION] == SDL_ENABLE ) {
  156.                 SDL_Event event;
  157.                 memset(&event, 0, sizeof(event));
  158.                 event.type = SDL_MOUSEMOTION;
  159.                 event.motion.state = buttonstate;
  160.                 event.motion.x = X;
  161.                 event.motion.y = Y;
  162.                 event.motion.xrel = Xrel;
  163.                 event.motion.yrel = Yrel;
  164.                 if ( (SDL_EventOK == NULL) || (*SDL_EventOK)(&event) ) {
  165.                         posted = 1;
  166.                         SDL_PushEvent(&event);
  167.                 }
  168.         }
  169.         return(posted);
  170. }
  171.  
  172. int SDL_PrivateMouseButton(Uint8 state, Uint8 button, Sint16 x, Sint16 y)
  173. {
  174.         SDL_Event event;
  175.         int posted;
  176.         int move_mouse;
  177.         Uint8 buttonstate;
  178.  
  179.         memset(&event, 0, sizeof(event));
  180.  
  181.         /* Check parameters */
  182.         if ( x || y ) {
  183.                 ClipOffset(&x, &y);
  184.                 move_mouse = 1;
  185.                 /* Mouse coordinates range from 0 - width-1 and 0 - height-1 */
  186.                 if ( x < 0 )
  187.                         x = 0;
  188.                 else
  189.                 if ( x >= SDL_VideoSurface->w )
  190.                         x = SDL_VideoSurface->w-1;
  191.  
  192.                 if ( y < 0 )
  193.                         y = 0;
  194.                 else
  195.                 if ( y >= SDL_VideoSurface->h )
  196.                         y = SDL_VideoSurface->h-1;
  197.         } else {
  198.                 move_mouse = 0;
  199.         }
  200.         if ( ! x )
  201.                 x = SDL_MouseX;
  202.         if ( ! y )
  203.                 y = SDL_MouseY;
  204.  
  205.         /* Figure out which event to perform */
  206.         buttonstate = SDL_ButtonState;
  207.         switch ( state ) {
  208.                 case SDL_PRESSED:
  209.                         event.type = SDL_MOUSEBUTTONDOWN;
  210.                         buttonstate |= SDL_BUTTON(button);
  211.                         break;
  212.                 case SDL_RELEASED:
  213.                         event.type = SDL_MOUSEBUTTONUP;
  214.                         buttonstate &= ~SDL_BUTTON(button);
  215.                         break;
  216.                 default:
  217.                         /* Invalid state -- bail */
  218.                         return(0);
  219.         }
  220.  
  221.         /* Update internal mouse state */
  222.         SDL_ButtonState = buttonstate;
  223.         if ( move_mouse ) {
  224.                 SDL_MouseX = x;
  225.                 SDL_MouseY = y;
  226.             /* We don't wan't the cursor because MenuetOS doesn't allow
  227.                hiding mouse cursor */
  228.         // uncommented for KolibriOS
  229.                 SDL_MoveCursor(SDL_MouseX, SDL_MouseY);
  230.         }
  231.  
  232.         /* Post the event, if desired */
  233.         posted = 0;
  234.         if ( SDL_ProcessEvents[event.type] == SDL_ENABLE ) {
  235.                 event.button.state = state;
  236.                 event.button.button = button;
  237.                 event.button.x = x;
  238.                 event.button.y = y;
  239.                 if ( (SDL_EventOK == NULL) || (*SDL_EventOK)(&event) ) {
  240.                         posted = 1;
  241.                         SDL_PushEvent(&event);
  242.                 }
  243.         }
  244.         return(posted);
  245. }
  246.  
  247.