Set EWMH active window to None when none has focus
_NET_ACTIVE_WINDOW: > The window ID of the currently active window or None if no window has > the focus. This fixes a bug that would not update _NET_ACTIVE_WINDOW when focus changed to an i3 container without a window such as a branch or workspace content container.
This commit is contained in:
parent
c7aae56030
commit
b4507da713
5
src/x.c
5
src/x.c
|
@ -1013,6 +1013,8 @@ void x_push_changes(Con *con) {
|
||||||
to_focus, focused, focused->name);
|
to_focus, focused, focused->name);
|
||||||
send_take_focus(to_focus, last_timestamp);
|
send_take_focus(to_focus, last_timestamp);
|
||||||
|
|
||||||
|
ewmh_update_active_window((con_has_managed_window(focused) ? focused->window->id : XCB_WINDOW_NONE));
|
||||||
|
|
||||||
if (to_focus != last_focused && is_con_attached(focused))
|
if (to_focus != last_focused && is_con_attached(focused))
|
||||||
ipc_send_window_event("focus", focused);
|
ipc_send_window_event("focus", focused);
|
||||||
} else {
|
} else {
|
||||||
|
@ -1030,7 +1032,7 @@ void x_push_changes(Con *con) {
|
||||||
xcb_change_window_attributes(conn, focused->window->id, XCB_CW_EVENT_MASK, values);
|
xcb_change_window_attributes(conn, focused->window->id, XCB_CW_EVENT_MASK, values);
|
||||||
}
|
}
|
||||||
|
|
||||||
ewmh_update_active_window(to_focus);
|
ewmh_update_active_window((con_has_managed_window(focused) ? focused->window->id : XCB_WINDOW_NONE));
|
||||||
|
|
||||||
if (to_focus != XCB_NONE && to_focus != last_focused && focused->window != NULL && is_con_attached(focused))
|
if (to_focus != XCB_NONE && to_focus != last_focused && focused->window != NULL && is_con_attached(focused))
|
||||||
ipc_send_window_event("focus", focused);
|
ipc_send_window_event("focus", focused);
|
||||||
|
@ -1043,6 +1045,7 @@ void x_push_changes(Con *con) {
|
||||||
if (focused_id == XCB_NONE) {
|
if (focused_id == XCB_NONE) {
|
||||||
DLOG("Still no window focused, better set focus to the root window\n");
|
DLOG("Still no window focused, better set focus to the root window\n");
|
||||||
xcb_set_input_focus(conn, XCB_INPUT_FOCUS_POINTER_ROOT, root, XCB_CURRENT_TIME);
|
xcb_set_input_focus(conn, XCB_INPUT_FOCUS_POINTER_ROOT, root, XCB_CURRENT_TIME);
|
||||||
|
ewmh_update_active_window(XCB_WINDOW_NONE);
|
||||||
focused_id = root;
|
focused_id = root;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -15,7 +15,8 @@
|
||||||
# (unless you are already familiar with Perl)
|
# (unless you are already familiar with Perl)
|
||||||
#
|
#
|
||||||
# Verifies that the _NET_ACTIVE_WINDOW message only changes focus when the
|
# Verifies that the _NET_ACTIVE_WINDOW message only changes focus when the
|
||||||
# window is on a visible workspace.
|
# window is on a visible workspace and that focus changes properly update this
|
||||||
|
# property on the root window.
|
||||||
# ticket #774, bug still present in commit 1e49f1b08a3035c1f238fcd6615e332216ab582e
|
# ticket #774, bug still present in commit 1e49f1b08a3035c1f238fcd6615e332216ab582e
|
||||||
# ticket #1136, bug still present in commit fd07f989fdf441ef335245dd3436a70ff60e8896
|
# ticket #1136, bug still present in commit fd07f989fdf441ef335245dd3436a70ff60e8896
|
||||||
use i3test;
|
use i3test;
|
||||||
|
@ -40,6 +41,23 @@ sub send_net_active_window {
|
||||||
$x->send_event(0, $x->get_root_window(), X11::XCB::EVENT_MASK_SUBSTRUCTURE_REDIRECT, $msg);
|
$x->send_event(0, $x->get_root_window(), X11::XCB::EVENT_MASK_SUBSTRUCTURE_REDIRECT, $msg);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
sub get_net_active_window {
|
||||||
|
my $cookie = $x->get_property(
|
||||||
|
0,
|
||||||
|
$x->get_root_window(),
|
||||||
|
$x->atom(name => '_NET_ACTIVE_WINDOW')->id,
|
||||||
|
$x->atom(name => 'WINDOW')->id,
|
||||||
|
0,
|
||||||
|
4096,
|
||||||
|
);
|
||||||
|
my $reply = $x->get_property_reply($cookie->{sequence});
|
||||||
|
my $len = $reply->{length};
|
||||||
|
|
||||||
|
return -1 if $len == 0;
|
||||||
|
return unpack("L", $reply->{value});
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
my $ws1 = fresh_workspace;
|
my $ws1 = fresh_workspace;
|
||||||
my $win1 = open_window;
|
my $win1 = open_window;
|
||||||
my $win2 = open_window;
|
my $win2 = open_window;
|
||||||
|
@ -113,4 +131,34 @@ send_net_active_window($scratch->id);
|
||||||
|
|
||||||
is($x->input_focus, $win3->id, 'window 3 still focused');
|
is($x->input_focus, $win3->id, 'window 3 still focused');
|
||||||
|
|
||||||
|
################################################################################
|
||||||
|
# Verify that the _NET_ACTIVE_WINDOW property is updated on the root window
|
||||||
|
# correctly.
|
||||||
|
################################################################################
|
||||||
|
|
||||||
|
fresh_workspace;
|
||||||
|
|
||||||
|
sync_with_i3;
|
||||||
|
|
||||||
|
is(get_net_active_window(), 0, 'workspace content focus is indicated by the root property as "None" window');
|
||||||
|
|
||||||
|
my $win4 = open_window;
|
||||||
|
|
||||||
|
cmd '[id="' . $win4->id . '"] focus';
|
||||||
|
|
||||||
|
sync_with_i3;
|
||||||
|
|
||||||
|
is(get_net_active_window(), $win4->id, 'window 4 is indicated as focused by the root property');
|
||||||
|
|
||||||
|
# make a branch
|
||||||
|
open_window;
|
||||||
|
open_window;
|
||||||
|
cmd 'split h';
|
||||||
|
open_window;
|
||||||
|
cmd 'focus parent';
|
||||||
|
|
||||||
|
sync_with_i3;
|
||||||
|
|
||||||
|
is(get_net_active_window(), 0, 'branch focus is indicated by the root property as "None" window');
|
||||||
|
|
||||||
done_testing;
|
done_testing;
|
||||||
|
|
Loading…
Reference in New Issue