我已经实现了一个基本的 x11 窗口应用程序。使用鼠标移动窗口后,
XGetWindowAttributes
始终返回相同的窗口位置(x
和y
结构中的XWindowAttributes
)。在 XSync(display, False);
之前调用 XGetWindowAttributes
没有帮助。为什么 XGetWindowAttributes
总是返回初始窗口位置?
这可能是由于窗口管理器装饰造成的。根据您的窗口管理器,当窗口管理器管理您的窗口时,它通常会向您的窗口添加装饰(例如标题栏、边框等),为此,窗口管理器可能会创建一个窗口frame,并且将窗口重新设置为创建的框架的父级。
根据功能手册:
x 和 y 成员设置为相对于由于您的窗口现在是所创建框架的子级,因此如果您使用鼠标移动框架,x 和 y 位置很可能不会改变,因为您实际上只是移动包含窗口的框架。父窗口原点的左上角外角。
要获取用户看到的窗口的
实际位置(包括窗口管理器添加的任何装饰),您需要使用XTranslateCoordinates
来平移窗口相对于根窗口的坐标,如@gkv311 在评论中说过。 欲了解更多信息,请查看
手册:
这是一个例子:
#include <X11/X.h>
#include <X11/Xlib.h>
#include <stdio.h>
int main() {
Display *display = XOpenDisplay(NULL);
if (display == NULL) {
fprintf(stderr, "Unable to open display\n");
return 1;
}
Window root = DefaultRootWindow(display);
int screen = DefaultScreen(display);
Window window = XCreateSimpleWindow(display, root, 100, 100, 640, 480, 1, BlackPixel(display, screen), WhitePixel(display, screen));
XSelectInput(display, window, StructureNotifyMask);
XMapWindow(display, window);
XEvent event;
while (1) {
XNextEvent(display, &event);
XWindowAttributes attrs;
XGetWindowAttributes(display, window, &attrs);
printf("Window position (XGetWindowAttributes): (%d, %d)\n", attrs.x, attrs.y);
int root_x, root_y;
Window child;
XTranslateCoordinates(display, window, root, 0, 0, &root_x, &root_y, &child);
printf("Window position (XTranslateCoordinates): (%d, %d)\n", root_x, root_y);
}
XCloseDisplay(display);
return 0;
}