pep*_*ico 6 x11 compiz ubuntu window-managers qt5
我已经创建了一个无框架Qt/QML窗口,我真的想知道任何设置其"Always On Top"系统菜单标志的程序化方法.单击ALT+SPACE我可以打开无框窗口的系统菜单,通过单击"始终在顶部"选项,窗口始终保持在顶部,但我没有找到一种编程方式来做同样的事情.这Qt.WindowStaysOnTopHint不起作用,尝试wmctrl -r "window name" -b add,above也不起作用,即使wmctrl它适用于其他窗口.wmctrl不适用于我感兴趣的窗口显然与N/A机器名称列有关wmctrl -l:
francisco@Ubuntu:~$ wmctrl -l
0x02600006 0 Ubuntu Área de trabalho
0x03c00002 0 Ubuntu XdndCollectionWindowImp
0x03c00005 0 Ubuntu unity-launcher
0x03c00008 0 Ubuntu unity-panel
0x03c0000b 0 Ubuntu unity-dash
0x03c0000c 0 Ubuntu Hud
0x046000b3 0 Ubuntu How to make a window aways on top? - Stack Overflow - Mozilla Firefox
0x0520000b 0 N/A Qt Creator
0x05002396 0 Ubuntu francisco@Ubuntu: ~
0x0540000b 0 N/A backlight
Run Code Online (Sandbox Code Playgroud)
我也经历过这个程序,但对于用户问,它也不适合我,同样的行为.该_NET_WM_STATE_ABOVE设置,但聚焦窗口,然后再次检查标志它不存在了,它通过点击系统菜单只有当是发粘.
这是QML:https://gist.github.com/oblitum/8050586
相关askubuntu问题:https://askubuntu.com/questions/394998
在相关的askubuntu问题中,发现wmctrl上应该存在一个错误,用于通过名称来定位某些窗口.使用wmctrl -i -r <window id> -b add,above也解决了这个问题.
EWMH规范明确指出:
_NET_WM_STATE_ABOVE和_NET_WM_STATE_BELOW主要用于用户首选项,不应被应用程序使用,例如用于引起对其对话框的注意(在这种情况下应使用紧急提示,请参阅"紧急度"一节).
所以窗口管理器没有责任尊重直接设置此属性的应用程序(即通过XChangeProperty).只能通过向窗口管理器侦听的根窗口发送客户端消息来更改此属性.
我不知道如何在像Qt这样的高级gui工具包中做到这一点,但这里是如何在普通的X11中做到这一点.(参见EWMH规范,或者_wnck_change_state用于示例实现).
//file: test.c
//to build it, run
//shell> gcc test.c -lX11
#include <X11/Xlib.h>
#define _NET_WM_STATE_REMOVE 0 /* remove/unset property */
#define _NET_WM_STATE_ADD 1 /* add/set property */
#define _NET_WM_STATE_TOGGLE 2 /* toggle property */
// change a window's _NET_WM_STATE property so that it can be kept on top.
// @display: x11 display singleton.
// @xid : the window to set on top.
Status x11_window_set_on_top (Display* display, Window xid)
{
XEvent event;
event.xclient.type = ClientMessage;
event.xclient.serial = 0;
event.xclient.send_event = True;
event.xclient.display = display;
event.xclient.window = xid;
event.xclient.message_type = XInternAtom (display, "_NET_WM_STATE", False);
event.xclient.format = 32;
event.xclient.data.l[0] = _NET_WM_STATE_ADD;
event.xclient.data.l[1] = XInternAtom (display, "_NET_WM_STATE_ABOVE", False);
event.xclient.data.l[2] = 0; //unused.
event.xclient.data.l[3] = 0;
event.xclient.data.l[4] = 0;
return XSendEvent (display, DefaultRootWindow(display), False,
SubstructureRedirectMask|SubstructureNotifyMask, &event);
}
// a sample main function for testing.
// shell> ./a.out window_xid
int main (int argc, char** argv)
{
Window xid = strtol (argv[1], NULL, 0);
Display* display = XOpenDisplay (NULL);
x11_window_set_on_top (display, xid);
XFlush (display); //for simplicity, no event loops here.
XCloseDisplay (display);
}
Run Code Online (Sandbox Code Playgroud)
另请注意,在某些x11环境(例如compiz)中,系统菜单由单独的装饰器程序而不是合成窗口管理器提供.
| 归档时间: |
|
| 查看次数: |
6382 次 |
| 最近记录: |