Skip to content

Commit

Permalink
Fixed bug #713
Browse files Browse the repository at this point in the history
Don't clamp the mouse coordinates to the video surface size, instead clamp them  to the last known window size.

This allows users to get the correct mouse coordinates even if they don't call SDL_SetVideoMode() in response to an SDL_VIDEORESIZE event (used as a hack to retain the OpenGL context on Windows and Linux after a window resize)
  • Loading branch information
slouken committed Sep 27, 2009
1 parent 9bc1ecc commit ac60885
Show file tree
Hide file tree
Showing 5 changed files with 24 additions and 15 deletions.
3 changes: 3 additions & 0 deletions src/events/SDL_events_c.h
Expand Up @@ -64,6 +64,9 @@ extern int SDL_PrivateExpose(void);
extern int SDL_PrivateQuit(void);
extern int SDL_PrivateSysWMEvent(SDL_SysWMmsg *message);

/* Used to clamp the mouse coordinates separately from the video surface */
extern void SDL_SetMouseRange(int maxX, int maxY);

/* Used by the activity event handler to remove mouse focus */
extern void SDL_ResetMouse(void);

Expand Down
33 changes: 19 additions & 14 deletions src/events/SDL_mouse.c
Expand Up @@ -34,6 +34,8 @@ static Sint16 SDL_MouseX = 0;
static Sint16 SDL_MouseY = 0;
static Sint16 SDL_DeltaX = 0;
static Sint16 SDL_DeltaY = 0;
static Sint16 SDL_MouseMaxX = 0;
static Sint16 SDL_MouseMaxY = 0;
static Uint8 SDL_ButtonState = 0;


Expand All @@ -45,6 +47,8 @@ int SDL_MouseInit(void)
SDL_MouseY = 0;
SDL_DeltaX = 0;
SDL_DeltaY = 0;
SDL_MouseMaxX = 0;
SDL_MouseMaxY = 0;
SDL_ButtonState = 0;

/* That's it! */
Expand Down Expand Up @@ -92,13 +96,19 @@ static void ClipOffset(Sint16 *x, Sint16 *y)
/* This clips absolute mouse coordinates when the apparent
display surface is smaller than the real display surface.
*/
if ( SDL_VideoSurface->offset ) {
if ( SDL_VideoSurface && SDL_VideoSurface->offset ) {
*y -= SDL_VideoSurface->offset/SDL_VideoSurface->pitch;
*x -= (SDL_VideoSurface->offset%SDL_VideoSurface->pitch)/
SDL_VideoSurface->format->BytesPerPixel;
}
}

void SDL_SetMouseRange(int maxX, int maxY)
{
SDL_MouseMaxX = (Sint16)maxX;
SDL_MouseMaxY = (Sint16)maxY;
}

/* These are global for SDL_eventloop.c */
int SDL_PrivateMouseMotion(Uint8 buttonstate, int relative, Sint16 x, Sint16 y)
{
Expand All @@ -107,11 +117,6 @@ int SDL_PrivateMouseMotion(Uint8 buttonstate, int relative, Sint16 x, Sint16 y)
Sint16 Xrel;
Sint16 Yrel;

/* Don't handle mouse motion if there's no cursor surface */
if ( SDL_VideoSurface == NULL ) {
return(0);
}

/* Default buttonstate is the current one */
if ( ! buttonstate ) {
buttonstate = SDL_ButtonState;
Expand All @@ -132,16 +137,16 @@ int SDL_PrivateMouseMotion(Uint8 buttonstate, int relative, Sint16 x, Sint16 y)
if ( x < 0 )
X = 0;
else
if ( x >= SDL_VideoSurface->w )
X = SDL_VideoSurface->w-1;
if ( x >= SDL_MouseMaxX )
X = SDL_MouseMaxX-1;
else
X = (Uint16)x;

if ( y < 0 )
Y = 0;
else
if ( y >= SDL_VideoSurface->h )
Y = SDL_VideoSurface->h-1;
if ( y >= SDL_MouseMaxY )
Y = SDL_MouseMaxY-1;
else
Y = (Uint16)y;

Expand Down Expand Up @@ -206,14 +211,14 @@ int SDL_PrivateMouseButton(Uint8 state, Uint8 button, Sint16 x, Sint16 y)
if ( x < 0 )
x = 0;
else
if ( x >= SDL_VideoSurface->w )
x = SDL_VideoSurface->w-1;
if ( x >= SDL_MouseMaxX )
x = SDL_MouseMaxX-1;

if ( y < 0 )
y = 0;
else
if ( y >= SDL_VideoSurface->h )
y = SDL_VideoSurface->h-1;
if ( y >= SDL_MouseMaxY )
y = SDL_MouseMaxY-1;
} else {
move_mouse = 0;
}
Expand Down
1 change: 1 addition & 0 deletions src/events/SDL_resize.c
Expand Up @@ -54,6 +54,7 @@ int SDL_PrivateResize(int w, int h)
((w == SDL_VideoSurface->w) && (h == SDL_VideoSurface->h)) ) {
return(0);
}
SDL_SetMouseRange(w, h);

/* Pull out all old resize events */
SDL_PeepEvents(events, sizeof(events)/sizeof(events[0]),
Expand Down
1 change: 1 addition & 0 deletions src/video/SDL_video.c
Expand Up @@ -639,6 +639,7 @@ SDL_Surface * SDL_SetVideoMode (int width, int height, int bpp, Uint32 flags)
/* Reset the keyboard here so event callbacks can run */
SDL_ResetKeyboard();
SDL_ResetMouse();
SDL_SetMouseRange(width, height);
SDL_cursorstate &= ~CURSOR_USINGSW;

/* Clean up any previous video mode */
Expand Down
1 change: 0 additions & 1 deletion src/video/wincommon/SDL_sysevents.c
Expand Up @@ -420,7 +420,6 @@ LRESULT CALLBACK WinMessage(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
/* Mouse is handled by DirectInput when fullscreen */
if ( SDL_VideoSurface && ! DINPUT() ) {
WORD xbuttonval = 0;
Sint16 x, y;
Uint8 button, state;

/* DJM:
Expand Down

0 comments on commit ac60885

Please sign in to comment.