Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

ShellClients: Allow X11 clients to use pantheon protocol via mutter hints #2002

Merged
merged 8 commits into from
Aug 8, 2024
81 changes: 80 additions & 1 deletion src/ShellClients/ShellClientsManager.vala
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,12 @@ public class Gala.ShellClientsManager : Object {
notifications_client = new NotificationsClient (wm.get_display ());

start_clients.begin ();

//X11 only
wm.get_display ().window_created.connect ((window) => {
window.notify["mutter-hints"].connect ((obj, pspec) => parse_mutter_hints ((Meta.Window) obj));
parse_mutter_hints (window);
});
leolost2605 marked this conversation as resolved.
Show resolved Hide resolved
}

private async void start_clients () {
Expand Down Expand Up @@ -98,7 +104,15 @@ public class Gala.ShellClientsManager : Object {
}
}

private void make_dock (Meta.Window window) {
public void make_dock (Meta.Window window) {
if (Meta.Util.is_wayland_compositor ()) {
make_dock_wayland (window);
} else {
make_dock_x11 (window);
}
}

private void make_dock_wayland (Meta.Window window) {
leolost2605 marked this conversation as resolved.
Show resolved Hide resolved
foreach (var client in protocol_clients) {
if (client.wayland_client.owns_window (window)) {
client.wayland_client.make_dock (window);
Expand All @@ -107,6 +121,25 @@ public class Gala.ShellClientsManager : Object {
}
}

private void make_dock_x11 (Meta.Window window) requires (!Meta.Util.is_wayland_compositor ()) {
unowned var x11_display = wm.get_display ().get_x11_display ();

#if HAS_MUTTER46
var x_window = x11_display.lookup_xwindow (window);
#else
var x_window = window.get_xwindow ();
#endif
// gtk3's gdk_x11_window_set_type_hint() is used as a reference
unowned var xdisplay = x11_display.get_xdisplay ();
var atom = xdisplay.intern_atom ("_NET_WM_WINDOW_TYPE", false);
var dock_atom = xdisplay.intern_atom ("_NET_WM_WINDOW_TYPE_DOCK", false);

// (X.Atom) 4 is XA_ATOM
// 32 is format
// 0 means replace
xdisplay.change_property (x_window, atom, (X.Atom) 4, 32, 0, (uchar[]) dock_atom, 1);
}

public void set_anchor (Meta.Window window, Meta.Side side) {
if (window in windows) {
windows[window].update_anchor (side);
Expand Down Expand Up @@ -156,4 +189,50 @@ public class Gala.ShellClientsManager : Object {

centered_windows[window] = new CenteredWindow (wm, window);
}

//X11 only
private void parse_mutter_hints (Meta.Window window) {
leolost2605 marked this conversation as resolved.
Show resolved Hide resolved
if (window.mutter_hints == null) {
return;
}

var mutter_hints = window.mutter_hints.split (":");
foreach (var mutter_hint in mutter_hints) {
var split = mutter_hint.split ("=");

if (split.length != 2) {
continue;
}

var key = split[0];
var val = split[1];

switch (key) {
case "anchor":
set_anchor (window, int.parse (val));
leolost2605 marked this conversation as resolved.
Show resolved Hide resolved
break;

case "hide-mode":
set_hide_mode (window, int.parse (val));
break;

case "size":
var split_val = val.split (",");
if (split_val.length != 2) {
break;
}
var width = int.parse (split_val[0]);
var height = int.parse (split_val[1]);
set_size (window, width, height);
break;

case "centered":
make_centered (window);
break;

default:
break;
}
}
}
}
Loading