We are currently migrating Bugzilla to GitHub issues.
Any changes made to the bug tracker now will be lost, so please do not post new bugs or make changes to them.
When we're done, all bug URLs will redirect to their equivalent location on the new bug tracker.

Bug 2542

Summary: Calling SDL_SetWindowGrab(SDL_FALSE) while window is minimized blocks until window is shown
Product: SDL Reporter: Lee Salzman <lsalzman>
Component: videoAssignee: Ryan C. Gordon <icculus>
Status: ASSIGNED --- QA Contact: Sam Lantinga <slouken>
Severity: normal    
Priority: P2    
Version: 2.0.3   
Hardware: All   
OS: Linux   

Description Lee Salzman 2014-05-12 19:41:24 UTC
In Tesseract, using SDL2 2.0.3, I have noticed that after I get a SDL_WINDOWEVENT_MINIMIZED event, signaling my window is minimized, on the subsequent SDL_WINDOWEVENT_LEAVE, I call SDL_SetWindowGrab(SDL_FALSE), which blocks indefinitely until the window is shown again.

The reason this is occuring is because I call SDL_SetRelativeMouseMode(SDL_FALSE) only AFTER that call to SDL_SetWindowGrab(SDL_FALSE), so this triggers an unfortunate cascade of wrongness:

void
SDL_UpdateWindowGrab(SDL_Window * window)
{
    if (_this->SetWindowGrab) {
        SDL_bool grabbed;
        if ((SDL_GetMouse()->relative_mode || (window->flags & SDL_WINDOW_INPUT_GRABBED)) &&
             (window->flags & SDL_WINDOW_INPUT_FOCUS)) {
            grabbed = SDL_TRUE;
        } else {
            grabbed = SDL_FALSE;
        }
        _this->SetWindowGrab(_this, window, grabbed);
    }
}

As here, relative_mode is true, but the window hasn't yet lost input focus, just mouse focus, even though SDL has just sent me a MINIMIZED windowevent. Now, probing deeper, this trigger this nasty surprise:

 void
X11_SetWindowGrab(_THIS, SDL_Window * window, SDL_bool grabbed)
{
...
    if (oldstyle_fullscreen || grabbed) {
        /* Try to grab the mouse */
        for (;;) {
            int result =
                X11_XGrabPointer(display, data->xwindow, True, 0, GrabModeAsync,
                             GrabModeAsync, data->xwindow, None, CurrentTime);
            if (result == GrabSuccess) {
                break;
            }
            SDL_Delay(50);
        }
...
}

It gets stuck in that loop because it is returning GrabNotViewable.
It would be saner here if SDL had some handling to release window grabs and relative mouse mode and restore them automagically when a window is minimized, so that way it wouldn't cause this issue...

Could also be some interaction between my window manager and this, but it doesn't seem so. I'm using PekWM in any case.
Comment 1 Sam Lantinga 2017-08-14 13:10:54 UTC
Hey Ryan, here's some insight into the window grab issues on X11.