Skip to content

Commit 3f39b01

Browse files
committed
x11: keep above
1 parent b8e9cf1 commit 3f39b01

File tree

1 file changed

+40
-0
lines changed

1 file changed

+40
-0
lines changed

safeeyes/ui/break_screen.py

+40
Original file line numberDiff line numberDiff line change
@@ -23,13 +23,15 @@
2323

2424
import gi
2525
from safeeyes import utility
26+
import Xlib
2627
from Xlib.display import Display
2728
from Xlib.display import X
2829

2930
gi.require_version("Gtk", "4.0")
3031
from gi.repository import Gdk
3132
from gi.repository import GLib
3233
from gi.repository import Gtk
34+
from gi.repository import GdkX11
3335

3436
BREAK_SCREEN_GLADE = os.path.join(utility.BIN_DIRECTORY, "glade/break_screen.glade")
3537

@@ -218,6 +220,9 @@ def __show_break_screen(self, message, image_path, widget, tray_actions):
218220
window.fullscreen_on_monitor(monitor)
219221
window.present()
220222

223+
if not self.context["is_wayland"]:
224+
self.__window_set_keep_above_x11(window)
225+
221226
if self.context["is_wayland"]:
222227
# this may or may not be granted by the window system
223228
window.get_surface().inhibit_system_shortcuts(None)
@@ -229,6 +234,41 @@ def __update_count_down(self, count):
229234
for label in self.count_labels:
230235
label.set_text(count)
231236

237+
def __window_set_keep_above_x11(self, window):
238+
"""Use EWMH hints to keep window above and on all desktops."""
239+
NET_WM_STATE = self.x11_display.intern_atom("_NET_WM_STATE")
240+
NET_WM_STATE_ABOVE = self.x11_display.intern_atom("_NET_WM_STATE_ABOVE")
241+
NET_WM_STATE_STICKY = self.x11_display.intern_atom("_NET_WM_STATE_STICKY")
242+
243+
# To change the _NET_WM_STATE, we cannot simply set the
244+
# property - we must send a ClientMessage event
245+
# See https://specifications.freedesktop.org/wm-spec/1.3/ar01s05.html#id-1.6.8
246+
root_window = self.x11_display.screen().root
247+
248+
xid = GdkX11.X11Surface.get_xid(window.get_surface())
249+
250+
root_window.send_event(
251+
Xlib.protocol.event.ClientMessage(
252+
window=xid,
253+
client_type=NET_WM_STATE,
254+
data=(
255+
32,
256+
[
257+
1, # _NET_WM_STATE_ADD
258+
NET_WM_STATE_ABOVE,
259+
NET_WM_STATE_STICKY, # other property
260+
1, # source indication
261+
0, # must be 0
262+
],
263+
),
264+
),
265+
event_mask=(
266+
Xlib.X.SubstructureRedirectMask | Xlib.X.SubstructureNotifyMask
267+
),
268+
)
269+
270+
self.x11_display.sync()
271+
232272
def __lock_keyboard_x11(self):
233273
"""Lock the keyboard to prevent the user from using keyboard shortcuts.
234274

0 commit comments

Comments
 (0)