diff options
author | Simon Hausmann <simon.hausmann@theqtcompany.com> | 2015-07-17 15:06:22 +0200 |
---|---|---|
committer | Simon Hausmann <simon.hausmann@theqtcompany.com> | 2015-07-17 16:35:42 +0200 |
commit | b2603b76655ac819e43c063bb6f16bc95f358083 (patch) | |
tree | 0fbe2c367ebfffdb70e9e3f21a7cf408bafd9626 /src/plugins/platforms/xcb | |
parent | 99b94aadf875c822afb6c2580e43355ac392ac92 (diff) | |
parent | 756266d01560157b7274e466b9ffc1b0e2ef9a1f (diff) |
Merge remote-tracking branch 'origin/5.5' into HEAD
Conflicts:
src/plugins/platforms/windows/qwindowsopengltester.cpp
Change-Id: Ia7abeba9395ccf84e2fa81b91a5725a86dedb9fe
Diffstat (limited to 'src/plugins/platforms/xcb')
-rw-r--r-- | src/plugins/platforms/xcb/qxcbconnection.cpp | 54 | ||||
-rw-r--r-- | src/plugins/platforms/xcb/qxcbconnection.h | 3 | ||||
-rw-r--r-- | src/plugins/platforms/xcb/qxcbscreen.cpp | 32 | ||||
-rw-r--r-- | src/plugins/platforms/xcb/qxcbscreen.h | 3 | ||||
-rw-r--r-- | src/plugins/platforms/xcb/qxcbwindow.cpp | 22 |
5 files changed, 77 insertions, 37 deletions
diff --git a/src/plugins/platforms/xcb/qxcbconnection.cpp b/src/plugins/platforms/xcb/qxcbconnection.cpp index f324942c8b..1fe46ff290 100644 --- a/src/plugins/platforms/xcb/qxcbconnection.cpp +++ b/src/plugins/platforms/xcb/qxcbconnection.cpp @@ -454,6 +454,7 @@ QXcbConnection::QXcbConnection(QXcbNativeInterface *nativeInterface, bool canGra , has_xkb(false) , m_buttons(0) , m_focusWindow(0) + , m_clientLeader(0) , m_systemTrayTracker(0) , m_glIntegration(Q_NULLPTR) , m_xiGrab(false) @@ -1336,6 +1337,58 @@ xcb_window_t QXcbConnection::rootWindow() return s ? s->root() : 0; } +xcb_window_t QXcbConnection::clientLeader() +{ + if (m_clientLeader == 0) { + m_clientLeader = xcb_generate_id(xcb_connection()); + QXcbScreen *screen = primaryScreen(); + Q_XCB_CALL(xcb_create_window(xcb_connection(), + XCB_COPY_FROM_PARENT, + m_clientLeader, + screen->root(), + 0, 0, 1, 1, + 0, + XCB_WINDOW_CLASS_INPUT_OUTPUT, + screen->screen()->root_visual, + 0, 0)); +#ifndef QT_NO_DEBUG + QByteArray ba("Qt client leader window"); + Q_XCB_CALL(xcb_change_property(xcb_connection(), + XCB_PROP_MODE_REPLACE, + m_clientLeader, + atom(QXcbAtom::_NET_WM_NAME), + atom(QXcbAtom::UTF8_STRING), + 8, + ba.length(), + ba.constData())); +#endif + Q_XCB_CALL(xcb_change_property(xcb_connection(), + XCB_PROP_MODE_REPLACE, + m_clientLeader, + atom(QXcbAtom::WM_CLIENT_LEADER), + XCB_ATOM_WINDOW, + 32, + 1, + &m_clientLeader)); + +#if !defined(QT_NO_SESSIONMANAGER) && defined(XCB_USE_SM) + // If we are session managed, inform the window manager about it + QByteArray session = qGuiApp->sessionId().toLatin1(); + if (!session.isEmpty()) { + Q_XCB_CALL(xcb_change_property(xcb_connection(), + XCB_PROP_MODE_REPLACE, + m_clientLeader, + atom(QXcbAtom::SM_CLIENT_ID), + XCB_ATOM_STRING, + 8, + session.length(), + session.constData())); + } +#endif + } + return m_clientLeader; +} + #ifdef XCB_USE_XLIB void *QXcbConnection::xlib_display() const { @@ -1578,6 +1631,7 @@ static const char * xcb_atomnames = { "_KDE_NET_WM_WINDOW_TYPE_OVERRIDE\0" "_KDE_NET_WM_FRAME_STRUT\0" + "_NET_FRAME_EXTENTS\0" "_NET_STARTUP_INFO\0" "_NET_STARTUP_INFO_BEGIN\0" diff --git a/src/plugins/platforms/xcb/qxcbconnection.h b/src/plugins/platforms/xcb/qxcbconnection.h index 90603ac9bc..7016b99425 100644 --- a/src/plugins/platforms/xcb/qxcbconnection.h +++ b/src/plugins/platforms/xcb/qxcbconnection.h @@ -194,6 +194,7 @@ namespace QXcbAtom { _KDE_NET_WM_WINDOW_TYPE_OVERRIDE, _KDE_NET_WM_FRAME_STRUT, + _NET_FRAME_EXTENTS, _NET_STARTUP_INFO, _NET_STARTUP_INFO_BEGIN, @@ -402,6 +403,7 @@ public: QXcbWMSupport *wmSupport() const { return m_wmSupport.data(); } xcb_window_t rootWindow(); + xcb_window_t clientLeader(); bool hasDefaultVisualId() const { return m_defaultVisualId != UINT_MAX; } xcb_visualid_t defaultVisualId() const { return m_defaultVisualId; } @@ -641,6 +643,7 @@ private: QXcbWindow *m_focusWindow; + xcb_window_t m_clientLeader; QByteArray m_startupId; QXcbSystemTrayTracker *m_systemTrayTracker; QXcbGlIntegration *m_glIntegration; diff --git a/src/plugins/platforms/xcb/qxcbscreen.cpp b/src/plugins/platforms/xcb/qxcbscreen.cpp index 040cea1cb2..c7f811491c 100644 --- a/src/plugins/platforms/xcb/qxcbscreen.cpp +++ b/src/plugins/platforms/xcb/qxcbscreen.cpp @@ -170,38 +170,6 @@ QXcbScreen::QXcbScreen(QXcbConnection *connection, QXcbVirtualDesktop *virtualDe else m_syncRequestSupported = true; - m_clientLeader = xcb_generate_id(xcb_connection()); - Q_XCB_CALL2(xcb_create_window(xcb_connection(), - XCB_COPY_FROM_PARENT, - m_clientLeader, - screen()->root, - 0, 0, 1, 1, - 0, - XCB_WINDOW_CLASS_INPUT_OUTPUT, - screen()->root_visual, - 0, 0), connection); -#ifndef QT_NO_DEBUG - QByteArray ba("Qt client leader window for screen "); - ba += m_outputName.toUtf8(); - Q_XCB_CALL2(xcb_change_property(xcb_connection(), - XCB_PROP_MODE_REPLACE, - m_clientLeader, - atom(QXcbAtom::_NET_WM_NAME), - atom(QXcbAtom::UTF8_STRING), - 8, - ba.length(), - ba.constData()), connection); -#endif - - Q_XCB_CALL2(xcb_change_property(xcb_connection(), - XCB_PROP_MODE_REPLACE, - m_clientLeader, - atom(QXcbAtom::WM_CLIENT_LEADER), - XCB_ATOM_WINDOW, - 32, - 1, - &m_clientLeader), connection); - xcb_depth_iterator_t depth_iterator = xcb_screen_allowed_depths_iterator(screen()); diff --git a/src/plugins/platforms/xcb/qxcbscreen.h b/src/plugins/platforms/xcb/qxcbscreen.h index 44519470e9..ccc30c0b84 100644 --- a/src/plugins/platforms/xcb/qxcbscreen.h +++ b/src/plugins/platforms/xcb/qxcbscreen.h @@ -116,8 +116,6 @@ public: xcb_randr_crtc_t crtc() const { return m_crtc; } xcb_randr_mode_t mode() const { return m_mode; } - xcb_window_t clientLeader() const { return m_clientLeader; } - void windowShown(QXcbWindow *window); QString windowManagerName() const { return m_windowManagerName; } bool syncRequestSupported() const { return m_syncRequestSupported; } @@ -173,7 +171,6 @@ private: Qt::ScreenOrientation m_orientation; QString m_windowManagerName; bool m_syncRequestSupported; - xcb_window_t m_clientLeader; QMap<xcb_visualid_t, xcb_visualtype_t> m_visuals; QMap<xcb_visualid_t, quint8> m_visualDepths; QXcbCursor *m_cursor; diff --git a/src/plugins/platforms/xcb/qxcbwindow.cpp b/src/plugins/platforms/xcb/qxcbwindow.cpp index 05d7292430..fb2fca43fa 100644 --- a/src/plugins/platforms/xcb/qxcbwindow.cpp +++ b/src/plugins/platforms/xcb/qxcbwindow.cpp @@ -623,7 +623,7 @@ void QXcbWindow::create() xcb_set_wm_hints(xcb_connection(), m_window, &hints); - xcb_window_t leader = platformScreen->clientLeader(); + xcb_window_t leader = connection()->clientLeader(); Q_XCB_CALL(xcb_change_property(xcb_connection(), XCB_PROP_MODE_REPLACE, m_window, atom(QXcbAtom::WM_CLIENT_LEADER), XCB_ATOM_WINDOW, 32, 1, &leader)); @@ -746,6 +746,22 @@ void QXcbWindow::setGeometry(const QRect &rect) QMargins QXcbWindow::frameMargins() const { if (m_dirtyFrameMargins) { + if (connection()->wmSupport()->isSupportedByWM(atom(QXcbAtom::_NET_FRAME_EXTENTS))) { + xcb_get_property_cookie_t cookie = xcb_get_property(xcb_connection(), false, m_window, + atom(QXcbAtom::_NET_FRAME_EXTENTS), XCB_ATOM_CARDINAL, 0, 4); + QScopedPointer<xcb_get_property_reply_t, QScopedPointerPodDeleter> reply( + xcb_get_property_reply(xcb_connection(), cookie, NULL)); + if (reply && reply->type == XCB_ATOM_CARDINAL && reply->format == 32 && reply->value_len == 4) { + quint32 *data = (quint32 *)xcb_get_property_value(reply.data()); + // _NET_FRAME_EXTENTS format is left, right, top, bottom + m_frameMargins = QMargins(data[0], data[2], data[1], data[3]); + m_dirtyFrameMargins = false; + return m_frameMargins; + } + } + + // _NET_FRAME_EXTENTS property is not available, so + // walk up the window tree to get the frame parent xcb_window_t window = m_window; xcb_window_t parent = m_window; @@ -859,7 +875,7 @@ void QXcbWindow::show() // Default to client leader if there is no transient parent, else modal dialogs can // be hidden by their parents. if (!transientXcbParent) - transientXcbParent = xcbScreen()->clientLeader(); + transientXcbParent = connection()->clientLeader(); if (transientXcbParent) { // ICCCM 4.1.2.6 Q_XCB_CALL(xcb_change_property(xcb_connection(), XCB_PROP_MODE_REPLACE, m_window, XCB_ATOM_WM_TRANSIENT_FOR, XCB_ATOM_WINDOW, 32, @@ -2446,6 +2462,8 @@ void QXcbWindow::handlePropertyNotifyEvent(const xcb_property_notify_event_t *ev m_windowState = newState; } return; + } else if (event->atom == atom(QXcbAtom::_NET_FRAME_EXTENTS)) { + m_dirtyFrameMargins = true; } else if (event->atom == atom(QXcbAtom::_NET_WORKAREA) && xcbScreen() && event->window == xcbScreen()->root()) { xcbScreen()->updateGeometry(event->time); } |