x11: don't hide cursor if window isn't focused

I found this sort of annoying.

You could argue that the "frontend" should maybe contain this logic, but
who cares.
This commit is contained in:
wm4 2018-10-11 06:38:57 +02:00 committed by Anton Kindestam
parent 19a38c4b1f
commit 8e3308d687
2 changed files with 35 additions and 22 deletions

View File

@ -248,7 +248,7 @@ static void x11_set_ewmh_state(struct vo_x11_state *x11, char *state, bool set)
x11_send_ewmh_msg(x11, "_NET_WM_STATE", params);
}
static void vo_set_cursor_hidden(struct vo *vo, bool cursor_hidden)
static void vo_update_cursor(struct vo *vo)
{
Cursor no_ptr;
Pixmap bm_no;
@ -258,16 +258,17 @@ static void vo_set_cursor_hidden(struct vo *vo, bool cursor_hidden)
struct vo_x11_state *x11 = vo->x11;
Display *disp = x11->display;
Window win = x11->window;
bool should_hide = x11->has_focus && !x11->mouse_cursor_visible;
if (cursor_hidden == x11->mouse_cursor_hidden)
if (should_hide == x11->mouse_cursor_set)
return;
x11->mouse_cursor_hidden = cursor_hidden;
x11->mouse_cursor_set = should_hide;
if (x11->parent == x11->rootwin || !win)
return; // do not hide if playing on the root window
if (x11->mouse_cursor_hidden) {
if (x11->mouse_cursor_set) {
colormap = DefaultColormap(disp, DefaultScreen(disp));
if (!XAllocNamedColor(disp, colormap, "black", &black, &dummy))
return; // color alloc failed, give up
@ -753,9 +754,6 @@ void vo_x11_uninit(struct vo *vo)
set_screensaver(x11, true);
if (x11->window != None)
vo_set_cursor_hidden(vo, false);
if (x11->window != None && x11->window != x11->rootwin) {
XUnmapWindow(x11->display, x11->window);
XDestroyWindow(x11->display, x11->window);
@ -1040,6 +1038,17 @@ static void vo_x11_check_net_wm_state_fullscreen_change(struct vo *vo)
}
}
// Releasing all keys on key-up or defocus is simpler and ensures no keys can
// get "stuck".
static void release_all_keys(struct vo *vo)
{
struct vo_x11_state *x11 = vo->x11;
if (x11->no_autorepeat)
mp_input_put_key(x11->input_ctx, MP_INPUT_RELEASE_ALL);
x11->win_drag_button1_down = false;
}
void vo_x11_check_events(struct vo *vo)
{
struct vo_x11_state *x11 = vo->x11;
@ -1091,16 +1100,18 @@ void vo_x11_check_events(struct vo *vo)
}
break;
}
// Releasing all keys in these situations is simpler and ensures no
// keys can be get "stuck".
case FocusOut:
case KeyRelease:
{
if (x11->no_autorepeat)
mp_input_put_key(x11->input_ctx, MP_INPUT_RELEASE_ALL);
x11->win_drag_button1_down = false;
case FocusIn:
x11->has_focus = true;
vo_update_cursor(vo);
break;
case FocusOut:
release_all_keys(vo);
x11->has_focus = false;
vo_update_cursor(vo);
break;
case KeyRelease:
release_all_keys(vo);
break;
}
case MotionNotify:
if (x11->win_drag_button1_down && !x11->fs &&
!mp_input_test_dragging(x11->input_ctx, Event.xmotion.x,
@ -1413,10 +1424,9 @@ static void vo_x11_create_window(struct vo *vo, XVisualInfo *vis,
Atom protos[1] = {XA(x11, WM_DELETE_WINDOW)};
XSetWMProtocols(x11->display, x11->window, protos, 1);
if (x11->mouse_cursor_hidden) {
x11->mouse_cursor_hidden = false;
vo_set_cursor_hidden(vo, true);
}
x11->mouse_cursor_set = false;
vo_update_cursor(vo);
if (x11->xim) {
x11->xic = XCreateIC(x11->xim,
XNInputStyle, XIMPreeditNone | XIMStatusNone,
@ -1858,7 +1868,8 @@ int vo_x11_control(struct vo *vo, int *events, int request, void *arg)
return VO_TRUE;
}
case VOCTRL_SET_CURSOR_VISIBILITY:
vo_set_cursor_hidden(vo, !(*(bool *)arg));
x11->mouse_cursor_visible = *(bool *)arg;
vo_update_cursor(vo);
return VO_TRUE;
case VOCTRL_KILL_SCREENSAVER:
set_screensaver(x11, false);

View File

@ -88,7 +88,9 @@ struct vo_x11_state {
bool pseudo_mapped; // not necessarily mapped, but known window size
int fs; // whether we assume the window is in fullscreen mode
bool mouse_cursor_hidden;
bool mouse_cursor_visible;
bool mouse_cursor_set;
bool has_focus;
long orig_layer;
// Current actual window position (updated on window move/resize events).