-
Notifications
You must be signed in to change notification settings - Fork 2.3k
Description
If the mouse is moving, and you disable relative mode and then warp the cursor, sometimes the cursor will not warp.
Code used to reproduce the issue:
#include <SDL.h>
#include <SDL_hints.h>
int main(int argc, char** args)
{
SDL_Init(SDL_INIT_EVENTS);
SDL_Window* win = SDL_CreateWindow("test window", 100, 100, 1200, 500, SDL_WINDOW_RESIZABLE);
SDL_SetHint(SDL_HINT_EVENT_LOGGING, "2");
bool loop = true;
bool relative = false;
SDL_SetRelativeMouseMode(SDL_bool::SDL_FALSE);
while (loop)
{
SDL_Event e;
while (SDL_PollEvent(&e) > 0)
{
if (e.type == SDL_EventType::SDL_KEYDOWN)
{
SDL_Keysym key = e.key.keysym;
if (key.sym == SDLK_b)
{
relative = !relative;
SDL_SetRelativeMouseMode(relative ? SDL_bool::SDL_TRUE : SDL_bool::SDL_FALSE);
if (!relative)
{
SDL_WarpMouseInWindow(win, 1000, 250);
SDL_Log("warp");
}
else
SDL_Log("toggle");
}
if (key.sym == SDLK_ESCAPE)
loop = false;
}
}
}
return 0;
}
video.mp4
How to reproduce:
- Press B once to enable relative mode (the OS cursor will dissapear)
- Start moving your mouse (I do it in a circle on the left side of the window, so it's easier to track)
- Press B to disable relative mode and warp the cursor
- The cursor will appear on the screen, but the location of the cursor is not predictable
The cursor is expected to be at the location that SDL_WarpMouseInWindow
specified (on the right side of the window, with my example code). Sometimes the cursor will appear here as expected.
But if the bug occurs, the cursor will not warp, and will appear on the location of the last SDL_MOUSEMOTION
event (on the left side in the video).
If you don't move your mouse, the cursor will always appear in the location specified by SDL_WarpMouseInWindow
.
There is a slight difference between the latest main
and 2.0.14
: On 2.0.14
it's the same as main
, but the cursor can also appear in the middle of the window.
Seems to happen much more frequently when mouse report rate is set to 1000 Hz. But I managed to reproduce it with 125 Hz, as seen in the logs below:
Normal logs:
INFO: SDL EVENT: SDL_MOUSEMOTION (timestamp=8916 windowid=1 which=0 state=0 x=83 y=116 xrel=29 yrel=-10)
INFO: SDL EVENT: SDL_MOUSEMOTION (timestamp=8923 windowid=1 which=0 state=0 x=122 y=104 xrel=39 yrel=-12)
INFO: SDL EVENT: SDL_MOUSEMOTION (timestamp=8932 windowid=1 which=0 state=0 x=167 y=94 xrel=45 yrel=-10)
INFO: SDL EVENT: SDL_KEYDOWN (timestamp=8936 windowid=1 state=pressed repeat=false scancode=5 keycode=98 mod=0)
INFO: SDL EVENT: SDL_TEXTINPUT (timestamp=8936 windowid=1 text='b')
INFO: warp
INFO: SDL EVENT: SDL_MOUSEMOTION (timestamp=8939 windowid=1 which=0 state=0 x=1035 y=243 xrel=868 yrel=149)
INFO: SDL EVENT: SDL_MOUSEMOTION (timestamp=8947 windowid=1 which=0 state=0 x=1050 y=242 xrel=15 yrel=-1)
INFO: SDL EVENT: SDL_MOUSEMOTION (timestamp=8955 windowid=1 which=0 state=0 x=1048 y=242 xrel=-2 yrel=0)
INFO: SDL EVENT: SDL_MOUSEMOTION (timestamp=8963 windowid=1 which=0 state=0 x=1034 y=248 xrel=-14 yrel=6)
Logs when the cursor doesn't warp:
INFO: SDL EVENT: SDL_MOUSEMOTION (timestamp=10211 windowid=1 which=0 state=0 x=182 y=259 xrel=-3 yrel=2)
INFO: SDL EVENT: SDL_MOUSEMOTION (timestamp=10219 windowid=1 which=0 state=0 x=187 y=258 xrel=5 yrel=-1)
INFO: SDL EVENT: SDL_MOUSEMOTION (timestamp=10227 windowid=1 which=0 state=0 x=201 y=253 xrel=14 yrel=-5)
INFO: SDL EVENT: SDL_KEYDOWN (timestamp=10235 windowid=1 state=pressed repeat=false scancode=5 keycode=98 mod=0)
INFO: SDL EVENT: SDL_TEXTINPUT (timestamp=10235 windowid=1 text='b')
INFO: warp
INFO: SDL EVENT: SDL_MOUSEMOTION (timestamp=10236 windowid=1 which=0 state=0 x=224 y=246 xrel=23 yrel=-7)
INFO: SDL EVENT: SDL_MOUSEMOTION (timestamp=10243 windowid=1 which=0 state=0 x=248 y=242 xrel=24 yrel=-4)
INFO: SDL EVENT: SDL_MOUSEMOTION (timestamp=10252 windowid=1 which=0 state=0 x=265 y=239 xrel=17 yrel=-3)
INFO: SDL EVENT: SDL_MOUSEMOTION (timestamp=10259 windowid=1 which=0 state=0 x=267 y=239 xrel=2 yrel=0)