Bug: SDL_WarpMouse does not change MouseState

First call of SDL_WarpMouse() wraps mouse cursor but does not change
mouse position returned by SDL_GetMouseState(). This happends when mouse
starts outside window. The position remains [0, 0].

The second call of SDL_WarpMouse() updates mouse position to right
values.

I attached test program which wraps mouse and 10 times prints mouse
position. Start with mouse out of window and don’t move it. Positions
will be [0, 0] instead of [320, 240].

System Information:
SDL 1.2.7
XFree86 Version 4.3.99.12–
Ivo Danihelka
-------------- next part --------------
A non-text attachment was scrubbed…
Name: main.c
Type: text/x-csrc
Size: 889 bytes
Desc: not available
URL: http://lists.libsdl.org/pipermail/sdl-libsdl.org/attachments/20040930/f3f5d2d4/attachment.c

Ivo Danihelka wrote:

First call of SDL_WarpMouse() wraps mouse cursor but does not change
mouse position returned by SDL_GetMouseState(). This happends when mouse
starts outside window. The position remains [0, 0].

The second call of SDL_WarpMouse() updates mouse position to right
values.

I attached test program which wraps mouse and 10 times prints mouse
position. Start with mouse out of window and don’t move it. Positions
will be [0, 0] instead of [320, 240].

System Information:
SDL 1.2.7
XFree86 Version 4.3.99.12

Hmm, that’s right.
The attached patch fixes it for me.

Stephane

-------------- next part --------------
An embedded and charset-unspecified text was scrubbed…
Name: mouse.patch
URL: http://lists.libsdl.org/pipermail/sdl-libsdl.org/attachments/20040930/479c8a84/attachment.asc

Stephane Marchesin wrote:

Ivo Danihelka wrote:

First call of SDL_WarpMouse() wraps mouse cursor but does not change
mouse position returned by SDL_GetMouseState(). This happends when mouse
starts outside window. The position remains [0, 0].
The second call of SDL_WarpMouse() updates mouse position to right
values.

I attached test program which wraps mouse and 10 times prints mouse
position. Start with mouse out of window and don’t move it. Positions
will be [0, 0] instead of [320, 240].

System Information:
SDL 1.2.7
XFree86 Version 4.3.99.12

Hmm, that’s right.
The attached patch fixes it for me.

Wait, this problem seems platform-independent. So the patch is too.

Stephane

-------------- next part --------------
An embedded and charset-unspecified text was scrubbed…
Name: mouse.patch
URL: http://lists.libsdl.org/pipermail/sdl-libsdl.org/attachments/20040930/0de6bad6/attachment.txt

Stephane Marchesin wrote:

Ivo Danihelka wrote:

First call of SDL_WarpMouse() wraps mouse cursor but does not change
mouse position returned by SDL_GetMouseState(). This happends when mouse
starts outside window. The position remains [0, 0].
The second call of SDL_WarpMouse() updates mouse position to right
values.

I attached test program which wraps mouse and 10 times prints mouse
position. Start with mouse out of window and don’t move it. Positions
will be [0, 0] instead of [320, 240].
[…]
Wait, this problem seems platform-independent. So the patch is too.

  •   if ( video->WarpWMCursor ) {
    
  •   if ( video->WarpWMCursor )
              video->WarpWMCursor(this, x, y);
    
  •   } else {
    
  •           SDL_PrivateMouseMotion(0, 0, x, y);
    
  •   }
    
  •   SDL_PrivateMouseMotion(0, 0, x, y);
    

Isn’t this the same problem like in the SDL cursor thread?

The system WarpWMCursor uses system calls, which use system events to update
the mouse position.
The SDL mouse position is updated not before a call to SDL_PumpEvents().

I am not sure whether disabling the support for warping the mouse via system
calls is good …
Perhaps calling always SDL_PrivateMouseMotion (whether we have WarpWMCursor or
not) might be reasonable …

Regards,
Johannes

< http://libufo.sourceforge.net > The OpenGL GUI ToolkitOn Thursday 30 September 2004 23:55, Stephane Marchesin wrote:

Johannes Schmidt wrote:

Wait, this problem seems platform-independent. So the patch is too.

  •   if ( video->WarpWMCursor ) {
    
  •   if ( video->WarpWMCursor )
             video->WarpWMCursor(this, x, y);
    
  •   } else {
    
  •           SDL_PrivateMouseMotion(0, 0, x, y);
    
  •   }
    
  •   SDL_PrivateMouseMotion(0, 0, x, y);
    

Isn’t this the same problem like in the SDL cursor thread?

Yes, you’re right. I’m quite busy these days and don’t read all the SDL
mailing list posts…

The system WarpWMCursor uses system calls, which use system events to update
the mouse position.
The SDL mouse position is updated not before a call to SDL_PumpEvents().

I am not sure whether disabling the support for warping the mouse via system
calls is good …
Perhaps calling always SDL_PrivateMouseMotion (whether we have WarpWMCursor or
not) might be reasonable …

At first sight, that sounds like the logical solution to me.

Stephane

I used SDL_PumpEvents() as you can see from the test program:On Fri, 2004-10-01 at 01:11, Johannes Schmidt wrote:

The SDL mouse position is updated not before a call to SDL_PumpEvents().


SDL_WarpMouse(screen->w / 2, screen->h / 2);

for (int i = 0; i < 10; ++i) {
    int x, y;
    SDL_PumpEvents();
    SDL_Delay(100);
    SDL_GetMouseState(&x, &y);
    fprintf(stderr, "curosr: %d, %d\n", x, y);
}

Probably system does not generate motion event as it should in this
case.


Ivo Danihelka

Oops, I haven’t read the original message, just Stephane’s reply :slight_smile:

If your mouse cursor is not within the SDL frame and you warp the mouse, you
get an enter notify, not a motion notify.
Therefore, SDL does not update its internal mouse state.

What’s about calling SDL_PrivateMouseMotion even when getting an EnterNotify?

Regards,
JohannesOn Friday 01 October 2004 02:30, Ivo Danihelka wrote:

On Fri, 2004-10-01 at 01:11, Johannes Schmidt wrote:

The SDL mouse position is updated not before a call to SDL_PumpEvents().

I used SDL_PumpEvents() as you can see from the test program:

SDL_WarpMouse(screen->w / 2, screen->h / 2);

for (int i = 0; i < 10; ++i) {
    int x, y;
    SDL_PumpEvents();
    SDL_Delay(100);
    SDL_GetMouseState(&x, &y);
    fprintf(stderr, "curosr: %d, %d\n", x, y);
}

Probably system does not generate motion event as it should in this
case.