Mercurial > minori
annotate dep/animia/src/win/x11.cc @ 158:80d6b28eb29f
dep/animia: fix most X11 stuff
it looks like _NET_WM_PID isn't supported by MOST clients, or my code is wrong...
core/filesystem: fix Linux config path handling on *nix
author | Paper <mrpapersonic@gmail.com> |
---|---|
date | Fri, 17 Nov 2023 02:07:33 -0500 |
parents | 18c8eb5d1edc |
children | 54c5d80a737e |
rev | line source |
---|---|
157 | 1 #include "animia/win/x11.h" |
2 #include "animia/win.h" | |
3 #include "animia.h" | |
4 | |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
5 #include <X11/Xlib.h> |
157 | 6 #include <X11/Xutil.h> |
7 #include <X11/Xatom.h> // XA_* | |
158
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
8 |
157 | 9 #include <cstdint> |
10 #include <string> | |
158
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
11 #include <memory> |
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
12 #include <set> |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
13 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
14 /* The code for this is very fugly because X11 uses lots of generic type names |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
15 (i.e., Window, Display), so I have to use :: when defining vars to distinguish |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
16 between Animia's types and X11's types */ |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
17 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
18 namespace animia::internal::x11 { |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
19 |
157 | 20 /* should return UTF8_STRING or STRING */ |
158
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
21 static bool GetWindowPropertyAsString(::Display* display, ::Window window, ::Atom atom, std::string& result, ::Atom reqtype = AnyPropertyType) { |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
22 int format; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
23 unsigned long leftover_bytes, num_of_items; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
24 ::Atom type; |
157 | 25 unsigned char* data; |
158
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
26 if (!::XGetWindowProperty(display, window, atom, 0L, (~0L), False, reqtype, |
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
27 &type, &format, &num_of_items, &leftover_bytes, &data)) |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
28 return false; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
29 |
157 | 30 result = std::string((char*)data, num_of_items); |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
31 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
32 return true; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
33 } |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
34 |
157 | 35 /* this should return CARDINAL, a 32-bit integer */ |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
36 static bool GetWindowPID(::Display* display, ::Window window, pid_t& result) { |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
37 int format; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
38 unsigned long leftover_bytes, num_of_items; |
158
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
39 ::Atom atom = ::XInternAtom(display, "_NET_WM_PID", False), type; |
157 | 40 unsigned char* data; |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
41 |
158
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
42 if (!::XGetWindowProperty(display, window, atom, 0L, (~0L), False, XA_CARDINAL, |
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
43 &type, &format, &num_of_items, &leftover_bytes, &data)) |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
44 return false; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
45 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
46 result = static_cast<pid_t>(*(uint32_t*)data); |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
47 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
48 return true; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
49 } |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
50 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
51 static bool FetchName(::Display* display, ::Window window, std::string& result) { |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
52 /* TODO: Check if XInternAtom created None or not... */ |
158
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
53 if (GetWindowPropertyAsString(display, window, ::XInternAtom(display, "_NET_WM_NAME", False), |
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
54 result, ::XInternAtom(display, "UTF8_STRING", False))) |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
55 return true; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
56 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
57 /* Fallback to XGetWMName() */ |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
58 XTextProperty text; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
59 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
60 { |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
61 int status = ::XGetWMName(display, window, &text); |
157 | 62 if (!status || !text.value || !text.nitems) |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
63 return false; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
64 } |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
65 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
66 char** list; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
67 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
68 { |
157 | 69 int count; |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
70 |
157 | 71 int status = ::XmbTextPropertyToTextList(display, &text, &list, &count); |
72 if (status < Success || !count || !*list) | |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
73 return false; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
74 } |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
75 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
76 ::XFree(text.value); |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
77 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
78 result = *list; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
79 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
80 ::XFreeStringList(list); |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
81 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
82 return true; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
83 } |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
84 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
85 bool X11WinTools::EnumerateWindows(window_proc_t window_proc) { |
158
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
86 if (!window_proc) |
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
87 return false; |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
88 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
89 ::Display* display = ::XOpenDisplay(nullptr); |
157 | 90 ::Window root = DefaultRootWindow(display); |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
91 |
158
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
92 unsigned int num_windows = 0; |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
93 ::Window* windows = nullptr; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
94 |
158
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
95 { |
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
96 ::Window root_return; |
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
97 ::Window parent_return; |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
98 |
158
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
99 int status = ::XQueryTree(display, root, &root_return, &parent_return, &windows, &num_windows); |
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
100 if (status < Success) |
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
101 return false; |
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
102 } |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
103 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
104 for (long k = 0; k < num_windows; k++) { |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
105 const ::Window window = windows[k]; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
106 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
107 Window win; |
158
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
108 win.id = window; |
157 | 109 { |
110 ::XClassHint* hint = ::XAllocClassHint(); | |
111 if (::XGetClassHint(display, window, hint)) { | |
112 win.class_name = hint->res_class; | |
113 ::XFree(hint); | |
114 } | |
115 } | |
116 FetchName(display, windows[k], win.text); | |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
117 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
118 Process proc; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
119 GetWindowPID(display, window, proc.pid); |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
120 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
121 if (!window_proc(proc, win)) |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
122 return false; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
123 } |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
124 |
158
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
125 ::XFree(windows); |
80d6b28eb29f
dep/animia: fix most X11 stuff
Paper <mrpapersonic@gmail.com>
parents:
157
diff
changeset
|
126 |
156
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
127 return true; |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
128 } |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
129 |
cdf79282d647
dep/animia: add VERY early x11 window stuff
Paper <mrpapersonic@gmail.com>
parents:
diff
changeset
|
130 } |