LINUX.ORG.RU

Xlib полноэкранное ли окно?

 ,


1

2

Весь интернет обшарил, но не нашел как определить является ли активное окно полноэкранным. Подозреваю, нужно использовать XGetWindowProperty, но с какими параметрами(а именно какой атом). Реквестую примеры. И, пользуясь случаем, хотел бы узнать, есть ли возможность посредством xlib засунуть иконку(используя pixmap или bitmap, ну или хотя бы просто символ) в трей.

P.S. Про возможности gtk и Qt мне известно поэтому не стоит о них упоминать. Интересует именно Xlib.



Последнее исправление: Yaourt (всего исправлений: 1)
Ответ на: комментарий от UVV

Не. Это я читал и нифига не понял. _NET_WM_STATE_FULLSCREEN всегда мне нули возвращает. Вот кусок кода:

    Atom type, filter;
    int format, status;
    unsigned long nitems, bytes_after;
    unsigned char *prop;

    filter = XInternAtom(display, "_NET_WM_STATE_FULLSCREEN", True);
    status = XGetWindowProperty(display, window, filter, 0, 256, False, AnyPropertyType,&type,
        &format, &nitems, &bytes_after, &prop);

printf("%s\n", prop);

Yaourt
() автор топика
Ответ на: комментарий от Zubok

Оно мне каждый раз разные цифры выдает для одного и того же клиента.

[nikita@laptop xlib_window]$ ./xgetfocus 
_NET_WM_PID: 22743
WM_CLASS: lxterminal
_NET_WM_NAME: nikita@laptop:~/Code/xlib_window
_NET_WM_STATE: 167920416
[nikita@laptop xlib_window]$ ./xgetfocus 
_NET_WM_PID: 22743
WM_CLASS: lxterminal
_NET_WM_NAME: nikita@laptop:~/Code/xlib_window
_NET_WM_STATE: 151925536
[nikita@laptop xlib_window]$ ./xgetfocus 
_NET_WM_PID: 22743
WM_CLASS: lxterminal
_NET_WM_NAME: nikita@laptop:~/Code/xlib_window
_NET_WM_STATE: 137507616

Yaourt
() автор топика
Ответ на: комментарий от Yaourt

Покажи код. Он возвращает список атомов. Список! То есть он тебе адрес возвращает, а он разный каждый раз. Смотри, что по ссылке написано.

Zubok ★★★★★
()
Последнее исправление: Zubok (всего исправлений: 3)
Ответ на: комментарий от Zubok
#include <X11/Xlib.h>
#include <X11/Xatom.h>
#include <stdio.h>
#include <stdlib.h>

Display *display;
unsigned long window;
unsigned char *prop;


unsigned char* get_string_property(char* property_name)
{
    Atom type, atom;
    int format, status;
    unsigned long nitems, bytes_after;

    atom = XInternAtom(display, property_name, True);
    status = XGetWindowProperty(display, window, atom, 0, 256, False, AnyPropertyType,
                                &type, &format, &nitems, &bytes_after, &prop);
    return prop;
}

unsigned long get_long_property(char* property_name)
{
    get_string_property(property_name);
    unsigned long long_property = prop[0] + (prop[1]<<8) + (prop[2]<<16) + (prop[3]<<24);
    return long_property;
}

int main(int argc, char** argv)
{

    display = XOpenDisplay(NULL);

    int screen = XDefaultScreen(display);
    window = RootWindow(display, screen);

    window = get_long_property("_NET_ACTIVE_WINDOW");

    printf("_NET_WM_PID: %lu\n", get_long_property("_NET_WM_PID"));
    printf("WM_CLASS: %s\n", get_string_property("WM_CLASS"));
    printf("_NET_WM_NAME: %s\n", get_string_property("_NET_WM_NAME"));
    printf("_NET_WM_STATE: %lu\n", get_string_property("_NET_WM_STATE"));

    XCloseDisplay(display);
    return 0;
}
Yaourt
() автор топика
Ответ на: комментарий от Yaourt

В prop - указатель на список атомов. nitems - число атомов. Бежишь по списку и ищешь filter. Вроде так. Мне для уточнения надо лезть в описание xlib. Если filter не найдет (filter - это атом из _NET_WM_STATE_FULLSCREEN), то, значит, нет fullscreen

A list of hints describing the window state. Atoms present in the list MUST be considered set, atoms not present in the list MUST be considered not set.

Zubok ★★★★★
()
Последнее исправление: Zubok (всего исправлений: 3)
Ответ на: комментарий от Zubok

Тут я как раз и не понимаю. Вот указатель _NET_WM_STATE я получил, как теперь из него _NET_WM_STATE_FULLSCREEN вытащить? Я пробовал получать _NET_WM_STATE_STICKY из prop таким способом: printf(«%d», prop[1]); и все получалось, но FULLSCREEN так не канает(пробовал prop[8])...

Yaourt
() автор топика
Ответ на: комментарий от Yaourt

Да нет же! Cписок атомов в документации это возможные значения. Они могут идти в любом порядке, они могут отсутствовать или присутствовать. У них нет фиксированных номеров. Надо бежать по списку prop[i] (от 0 до nitems-1) и искать filter.

Zubok ★★★★★
()
Ответ на: комментарий от Zubok

Блин, теперь я не знаю как искать атом в списке. Допустим, циклом перебираю значения по одному, как узнать, что мне попалось искомое значение? XInternAtom? Оно атом просит, а не prop...

Yaourt
() автор топика
Ответ на: комментарий от Yaourt

Делаешь

filter = XInternAtom(display, "_NET_WM_STATE_FULLSCREEN", False);
net_wm_state = XInternAtom(display, "_NET_WM_STATE", False);

Потом получаешь свойство net_wm_state, получаешь prop, ищешь в prop filter

UPD. Подправил.

Zubok ★★★★★
()
Последнее исправление: Zubok (всего исправлений: 3)
Ответ на: комментарий от Zubok

Я сейчас с ума сойду. Говорю же, что не знаю как искать атом(filter) в prop. По порядку: получил фильтр, получил стейт, получил проп из стейта, дальше как, что с чем сравнивать?

Yaourt
() автор топика
Ответ на: комментарий от Yaourt

Atom *prop;

...

for (i = 0; i < nitems; i++) {
    if (prop[i] == filter) {
        BINGO!!!
        XFree(prop);
        return TRUE;
    }
}

XFree(prop);
return FALSE;

+ проверь перед обходом, что nitems > 0

Zubok ★★★★★
()
Последнее исправление: Zubok (всего исправлений: 6)
Ответ на: комментарий от Zubok

Не, не так. При переборе на том же окне(фуллскрин и не фуллскрин) параметры отличаются, как и должно быть, но они ни одно не соответствует значению фильтра. Кусок кода и вывод(на окне простом Chrome, потом на фуллскрин):

    filter = XInternAtom(display, "_NET_WM_STATE_FULLSCREEN", 1);
    net_wm_state = XInternAtom(display, "_NET_WM_STATE", 1);
    
    Atom type, atom, *prop1;
    int format, status;
    unsigned long nitems, bytes_after;

    status = XGetWindowProperty(display, window, net_wm_state, 0, 10000, False, AnyPropertyType,
                                prop1, &format, &nitems, &bytes_after, &prop);
                                
    printf("FULL %d\nNITEM %d\n", filter,nitems );
    int i;
    if (nitems != 0){
    for (i = 0; i < nitems; i++) { /* проверка через Atom* */
        printf("    %d\n", prop1[i]);    
    }
    printf("-----\n");
    for (i = 0; i < nitems; i++) { /* проверка через unsigned char** */
        printf("    %d\n", prop[i]);    
    }
}

ВЫВОД
[nikita@laptop xlib_window]$ sleep 3 && ./xgetfocus 
FULL 359
NITEM 2
    4
    0
-----
    101
    1
[nikita@laptop xlib_window]$ sleep 3 && ./xgetfocus 
FULL 359
NITEM 3
    4
    0
    -1075594775
-----
    101
    1
    0
[nikita@laptop xlib_window]$ 

Yaourt
() автор топика
Ответ на: комментарий от Yaourt

Давай разложу на кусочки, чтобы понятнее:

Atom *atoms;

filter = XInternAtom(display, "_NET_WM_STATE_FULLSCREEN", False);
net_wm_state = XInternAtom(display, "_NET_WM_STATE", False);

status = XGetWindowProperty(... , &prop);
atoms = (Atom *)prop;

for (i = 0; i < nitems; i++) {
    printf("    %d\n", atoms[i]);
}

И ты уверен, что у тебя твое окно fullscreen? Проверь через утилиту xprop, она показывает список _NET_WM_STATE.

Zubok ★★★★★
()
Последнее исправление: Zubok (всего исправлений: 2)
Ответ на: комментарий от Yaourt

У тебя тут все неправильно вообще.

status = XGetWindowProperty(display, window, net_wm_state, 0, LONG_MAX, False, XA_ATOM,
                            &type, &format, &nitems, &bytes_after, (unsigned char **)&prop);

с чего ты вдруг prop1 выводишь? Туда *тип* возвращается, а не атом. Там будет XA_ATOM.

Zubok ★★★★★
()
Последнее исправление: Zubok (всего исправлений: 1)
Ответ на: комментарий от Yaourt

Вот я быстро накидал. Это работает. Вместо window надо идентификатор окна поставить. Не знаю, как ты его захватываешь в своей программе.

#include <X11/Xlib.h>
#include <X11/Xatom.h>
#include <stdio.h>
#include <stdlib.h>
#include <limits.h>

Display *display;
unsigned long window;

int main(int argc, char** argv)
{

    Atom filter, net_wm_state, type;
    int i, format, status;
    unsigned long nitems, bytes_after;
    Atom *atoms;
    unsigned char *prop;

    display = XOpenDisplay(NULL);

    filter = XInternAtom(display, "_NET_WM_STATE_FULLSCREEN", False);
    net_wm_state = XInternAtom(display, "_NET_WM_STATE", False);

    status = XGetWindowProperty(display, window, net_wm_state, 0, LONG_MAX, 
				False, XA_ATOM, &type, &format, &nitems, 
				&bytes_after, &prop);
    atoms = (Atom *)prop;

    for (i = 0; i < nitems; i++) {
	if (atoms[i] == filter) {
	    printf("Fullscreen!\n");
	} 
    }
    
    XFree(prop);
    XCloseDisplay(display);
    return 0;
}
Zubok ★★★★★
()
Последнее исправление: Zubok (всего исправлений: 2)
Ответ на: комментарий от Zubok

Ну еще раз спасибо, сам бы вряд ли разобрался. А насчет иконки или просто места в трее не подскажешь?

Yaourt
() автор топика

Вкусная тема, жаль на ЛОРе редко обсуждения на таком уровне проходят.

// Сам xlib не осилил, пишу на Qt.

hobbit ★★★★★
()
Ответ на: комментарий от Yaourt

Только я не очень понял, почему ты в программе передаешь RootWindow. Тебе надо идентификатор конкретного окна передать.

Zubok ★★★★★
()
Ответ на: комментарий от Zubok

Да то для примера. Так я беру окно на котором инпутфокус XGetInputFocus().

Yaourt
() автор топика

И, пользуясь случаем, хотел бы узнать, есть ли возможность посредством xlib засунуть иконку(используя pixmap или bitmap, ну или хотя бы просто символ) в трей.

Если речь идет про системный трей, то нужно читать:

http://standards.freedesktop.org/systemtray-spec/systemtray-spec-0.3.html

И XEMBED:

http://standards.freedesktop.org/xembed-spec/xembed-spec-latest.html

Сложное чтение. Ищи примеры в сети.

Zubok ★★★★★
()
Ответ на: комментарий от Yaourt

В принципе, из соображений пуризма теперь можешь убрать atoms. Я ее использовал выше там в примере, чтобы понятно было, что и откуда берется. Сейчас можно заменить:

Atom *prop;
/* Atom *atoms; <----- убрать */
...
status = XGetWindowProperty(... (unsigned char **)&prop); /* замена */

/* atoms = (Atom *)prop;  <----- убрать */

...
    if (prop[i] == filter) {  /* замена */

Ну и лучше всего проверять status, а также, что prop не NULL. Не забывать при любом исходе делать XFree(prop).

Zubok ★★★★★
()
29 июня 2016 г.
Ответ на: комментарий от Zubok

активное окно

Добрый день!

в терминале запускаю программу с таким кодом:

Display *display = XOpenDisplay(NULL); Window win, root, parent, *children; int revert = RevertToParent; int screen = DefaultScreen(display); unsigned int nchild; XGetInputFocus(display, &win, &revert); XDestroyWindow(display, win);

то есть хочу получить активное (как я думаю это терминал) окно и тут же его закрыть .

но терминал не закрывается.

подскажите что не так?

mixa
()
Ответ на: активное окно от mixa

Ой, только сейчас заметил среди уведомлений, что есть вопрос в старую тему. Вообще, лучше новую тему всегда создавать по другому вопросу. Тут-то совсем другой вопрос обсуждается.

Ладно, а сравнивал window id, который ты получил из XGetInputFocus и window id, который возвращает программа xprop, например. Ведь фокус может иметь не top level window приложения, а какой-то его сотый потомок (он же тоже окно). Иксы - это просто древовидная иерархия окон. И в них нет понятия окна приложения. Это понятие есть в ICCCM и EWMH. В иерархии окон терминала может быть несколько окон. И ты пытаешься закрыть какое-то субокно. В общем, ты сначала сравни то, о чем я в первой строчке спросил.

И вот еще ветка про поиск Top level window в иерархии окон. Мне кажется, она к твоему вопросу имеет прямое отношение. В конце есть код:

XGetInputFocus возвращает неверное значение

Zubok ★★★★★
()
Последнее исправление: Zubok (всего исправлений: 1)
Ответ на: комментарий от Zubok

В конце есть код:

только там в момент поиска по результатам XQueryTree надо сграбить сервер, чтобы структура, пока ты ищешь нужное окно, не поменялась. После поиска, ungrab сделать. XGrabServer/XUngrabServer.

Zubok ★★★★★
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.