2015-05-12 5 views
5

Мне удалось отобразить окно с помощью XIconifyWindow, но не удалось его восстановить позже. Я попытался следующие:Как восстановить окно с помощью Xlib?

XMapRaised (display, window); 

И:

XMapWindow (display, window); 

И:

XClientMessageEvent ev; 
std::memset (&ev, 0, sizeof ev); 
ev.type = ClientMessage; 
ev.window = window; 
ev.message_type = XInternAtom(display, "WM_CHANGE_STATE", False); 
ev.format = 32; 
ev.data.l[0] = NormalState; 
XSendEvent (display, RootWindow(display, XDefaultScreen(display)), False, 
    SubstructureRedirectMask |SubstructureNotifyMask, (XEvent*)&ev); 
XFlush (display); 

К без успеха. Я использую Debian Jessie с GNOME 3.14.0.

+0

Вы пытались отправить сообщение 'WM_CHANGE_STATE' с элементом данных из' NormalState'? (Хотя я бы предположил, что «XMapRaised» неправильно отобразил окно правильно, вы уверены, что вы сбросили вызовы/ждали сервера? Вы также убедились, что вы вызвали это в правильном окне верхнего уровня и не ушли предка, обозначенного/снятого?) –

+0

Нет, но теперь я пробовал это и, к сожалению, он не работает. У меня есть только одно окно, так что очевидно, что это верхний уровень. Я также попытался добавить «XFlush» без успеха. Надеюсь, мне не придется в конечном итоге использовать код, специфичный для WM. –

+0

Можете ли вы разместить соответствующие части кода здесь? Включая различные попытки, которые вы сделали? –

ответ

4

После того, как много пушек, наконец, решили!

В GNOME 3 окна не имеют кнопки «iconify/minim». Похоже, что окно не может быть минимизировано ни пользователем, ни кодом. Когда я позвонил XIconifyWindow, окно не было сведено к минимуму. Если бы это было сведено к минимуму, я бы получил событие «UnmapNotify», которого я не сделал. Что произошло, окно было скрыто («_NET_WM_STATE_HIDDEN» было добавлено в свойство «_NET_WM_STATE» окна), а другое окно было активировано. Так что все, что я должен был сделать, чтобы «unminimize» окно было активировать его:

XClientMessageEvent ev; 
std::memset (&ev, 0, sizeof ev); 
ev.type = ClientMessage; 
ev.window = window; 
ev.message_type = XInternAtom(display, "_NET_ACTIVE_WINDOW", True); 
ev.format = 32; 
ev.data.l[0] = 1; 
ev.data.l[1] = CurrentTime; 
ev.data.l[2] = ev.data.l[3] = ev.data.l[4] = 0; 
XSendEvent (display, RootWindow(display, XDefaultScreen(display)), False, 
    SubstructureRedirectMask |SubstructureNotifyMask, (XEvent*)&ev); 
XFlush (display); 

Btw вызова XRaiseWindow вместо не работает, похоже, она должна была быть активирована.

+0

Красиво найден. Это кажется мне немного сломанным. Отправка '_NET_ACTIVE_WINDOW' отличается от« отображения »окна (хотя оно должно отображать окно), но также подразумевает, что запрос на это окно становится активным окном (которое может или не может быть действительно желательным). Я бы ожидал, что «XMapRaised» или подобное сработало бы, но, возможно, нет. И я не вижу ничего очевидного в wm-spec о том, как отменить 'HIDDEN'. –