diff options
author | Liang Qi <liang.qi@theqtcompany.com> | 2015-03-31 18:47:56 +0200 |
---|---|---|
committer | Liang Qi <liang.qi@theqtcompany.com> | 2015-04-01 09:10:26 +0200 |
commit | 0e6ee136c91432d4ceeeda64e5a5fa88231398d4 (patch) | |
tree | 6060e002af2900007895f6efa757989dd4c190c9 /src/plugins/platforms/xcb | |
parent | 418869d9158ea5cd998ba30778b0b7173b48161b (diff) | |
parent | 17294c5e4d15d5776f6e414b03671a4a9ed4993d (diff) |
Merge remote-tracking branch 'origin/5.5' into dev
Conflicts:
src/testlib/qtestblacklist.cpp
src/widgets/accessible/qaccessiblewidgets.cpp
Change-Id: If032adb9296428f62384ed835dbf41ee7a0b886c
Diffstat (limited to 'src/plugins/platforms/xcb')
-rw-r--r-- | src/plugins/platforms/xcb/qxcbbackingstore.cpp | 60 | ||||
-rw-r--r-- | src/plugins/platforms/xcb/qxcbbackingstore.h | 3 | ||||
-rw-r--r-- | src/plugins/platforms/xcb/qxcbclipboard.cpp | 3 | ||||
-rw-r--r-- | src/plugins/platforms/xcb/qxcbconnection.cpp | 140 | ||||
-rw-r--r-- | src/plugins/platforms/xcb/qxcbconnection.h | 1 | ||||
-rw-r--r-- | src/plugins/platforms/xcb/qxcbcursor.cpp | 12 | ||||
-rw-r--r-- | src/plugins/platforms/xcb/qxcbintegration.cpp | 9 | ||||
-rw-r--r-- | src/plugins/platforms/xcb/qxcbwindow.cpp | 76 | ||||
-rw-r--r-- | src/plugins/platforms/xcb/qxcbwindow.h | 2 |
9 files changed, 225 insertions, 81 deletions
diff --git a/src/plugins/platforms/xcb/qxcbbackingstore.cpp b/src/plugins/platforms/xcb/qxcbbackingstore.cpp index ce2329724a..06db4d83ac 100644 --- a/src/plugins/platforms/xcb/qxcbbackingstore.cpp +++ b/src/plugins/platforms/xcb/qxcbbackingstore.cpp @@ -303,21 +303,30 @@ QXcbBackingStore::~QXcbBackingStore() QPaintDevice *QXcbBackingStore::paintDevice() { - return m_image ? m_image->image() : 0; + if (!m_image) + return 0; + return m_rgbImage.isNull() ? m_image->image() : &m_rgbImage; } void QXcbBackingStore::beginPaint(const QRegion ®ion) { if (!m_image) return; - const int dpr = int(m_image->image()->devicePixelRatio()); - QRegion xRegion = dpr == 1 ? region : QTransform::fromScale(dpr,dpr).map(region); - m_image->preparePaint(xRegion); + + int dpr = int(m_image->image()->devicePixelRatio()); + const int windowDpr = int(window()->devicePixelRatio()); + if (windowDpr != dpr) { + resize(window()->size(), QRegion()); + dpr = int(m_image->image()->devicePixelRatio()); + } + + m_paintRegion = dpr == 1 ? region : QTransform::fromScale(dpr,dpr).map(region); + m_image->preparePaint(m_paintRegion); if (m_image->image()->hasAlphaChannel()) { - QPainter p(m_image->image()); + QPainter p(paintDevice()); p.setCompositionMode(QPainter::CompositionMode_Source); - const QVector<QRect> rects = xRegion.rects(); + const QVector<QRect> rects = m_paintRegion.rects(); const QColor blank = Qt::transparent; for (QVector<QRect>::const_iterator it = rects.begin(); it != rects.end(); ++it) { p.fillRect(*it, blank); @@ -325,6 +334,24 @@ void QXcbBackingStore::beginPaint(const QRegion ®ion) } } +void QXcbBackingStore::endPaint() +{ + QXcbWindow *platformWindow = static_cast<QXcbWindow *>(window()->handle()); + if (!platformWindow || !platformWindow->imageNeedsRgbSwap()) + return; + + // Slow path: the paint device was m_rgbImage. Now copy with swapping red + // and blue into m_image. + const QVector<QRect> rects = m_paintRegion.rects(); + if (rects.isEmpty()) + return; + QPainter p(m_image->image()); + for (QVector<QRect>::const_iterator it = rects.begin(); it != rects.end(); ++it) { + const QRect rect = *it; + p.drawImage(rect.topLeft(), m_rgbImage.copy(rect).rgbSwapped()); + } +} + #ifndef QT_NO_OPENGL QImage QXcbBackingStore::toImage() const { @@ -342,7 +369,15 @@ void QXcbBackingStore::flush(QWindow *window, const QRegion ®ion, const QPoin if (!m_image || m_image->size().isEmpty()) return; - QSize imageSize = m_image->size(); + const int dpr = int(window->devicePixelRatio()); + +#ifndef QT_NO_DEBUG + const int imageDpr = int(m_image->image()->devicePixelRatio()); + if (dpr != imageDpr) + qWarning() << "QXcbBackingStore::flush() wrong devicePixelRatio for backingstore image" << dpr << imageDpr; +#endif + + QSize imageSize = m_image->size() / dpr; //because we multiply with the DPR later QRegion clipped = region; clipped &= QRect(0, 0, window->width(), window->height()); @@ -361,8 +396,6 @@ void QXcbBackingStore::flush(QWindow *window, const QRegion ®ion, const QPoin return; } - const int dpr = int(window->devicePixelRatio()); - QVector<QRect> rects = clipped.rects(); for (int i = 0; i < rects.size(); ++i) { QRect rect = QRect(rects.at(i).topLeft() * dpr, rects.at(i).size() * dpr); @@ -399,8 +432,7 @@ void QXcbBackingStore::resize(const QSize &size, const QRegion &) { const int dpr = int(window()->devicePixelRatio()); const QSize xSize = size * dpr; - - if (m_image && xSize == m_image->size()) + if (m_image && xSize == m_image->size() && dpr == m_image->image()->devicePixelRatio()) return; Q_XCB_NOOP(connection()); @@ -415,6 +447,12 @@ void QXcbBackingStore::resize(const QSize &size, const QRegion &) delete m_image; m_image = new QXcbShmImage(screen, xSize, win->depth(), win->imageFormat()); m_image->image()->setDevicePixelRatio(dpr); + // Slow path for bgr888 VNC: Create an additional image, paint into that and + // swap R and B while copying to m_image after each paint. + if (win->imageNeedsRgbSwap()) { + m_rgbImage = QImage(xSize, win->imageFormat()); + m_rgbImage.setDevicePixelRatio(dpr); + } Q_XCB_NOOP(connection()); } diff --git a/src/plugins/platforms/xcb/qxcbbackingstore.h b/src/plugins/platforms/xcb/qxcbbackingstore.h index 248542719b..b58a32d313 100644 --- a/src/plugins/platforms/xcb/qxcbbackingstore.h +++ b/src/plugins/platforms/xcb/qxcbbackingstore.h @@ -65,9 +65,12 @@ public: bool scroll(const QRegion &area, int dx, int dy) Q_DECL_OVERRIDE; void beginPaint(const QRegion &) Q_DECL_OVERRIDE; + void endPaint() Q_DECL_OVERRIDE; private: QXcbShmImage *m_image; + QRegion m_paintRegion; + QImage m_rgbImage; }; QT_END_NAMESPACE diff --git a/src/plugins/platforms/xcb/qxcbclipboard.cpp b/src/plugins/platforms/xcb/qxcbclipboard.cpp index 2c0a7a11cc..248d1b4bbb 100644 --- a/src/plugins/platforms/xcb/qxcbclipboard.cpp +++ b/src/plugins/platforms/xcb/qxcbclipboard.cpp @@ -749,7 +749,8 @@ void QXcbClipboard::handleXFixesSelectionRequest(xcb_xfixes_selection_notify_eve m_xClipboard[mode]->reset(); } emitChanged(mode); - } else if (event->subtype == XCB_XFIXES_SELECTION_EVENT_SELECTION_CLIENT_CLOSE) + } else if (event->subtype == XCB_XFIXES_SELECTION_EVENT_SELECTION_CLIENT_CLOSE || + event->subtype == XCB_XFIXES_SELECTION_EVENT_SELECTION_WINDOW_DESTROY) emitChanged(mode); } diff --git a/src/plugins/platforms/xcb/qxcbconnection.cpp b/src/plugins/platforms/xcb/qxcbconnection.cpp index 0ca141526e..706b9c8e48 100644 --- a/src/plugins/platforms/xcb/qxcbconnection.cpp +++ b/src/plugins/platforms/xcb/qxcbconnection.cpp @@ -306,71 +306,88 @@ void QXcbConnection::initializeScreens() int connectedOutputCount = 0; if (has_randr_extension) { xcb_generic_error_t *error = NULL; - xcb_randr_get_output_primary_cookie_t primaryCookie = - xcb_randr_get_output_primary(xcb_connection(), xcbScreen->root); - // TODO: RRGetScreenResources has to be called on each X display at least once before - // RRGetScreenResourcesCurrent can be used - we can't know if we are the first application - // to do so or not, so we always call the slower version here. Ideally we should share some - // global flag (an atom on root window maybe) that at least other Qt apps would understand - // and could call RRGetScreenResourcesCurrent here, speeding up start. - xcb_randr_get_screen_resources_cookie_t resourcesCookie = - xcb_randr_get_screen_resources(xcb_connection(), xcbScreen->root); - QScopedPointer<xcb_randr_get_output_primary_reply_t, QScopedPointerPodDeleter> primary( - xcb_randr_get_output_primary_reply(xcb_connection(), primaryCookie, &error)); - if (!primary || error) { - qWarning("failed to get the primary output of the screen"); + // RRGetScreenResourcesCurrent is fast but it may return nothing if the + // configuration is not initialized wrt to the hardware. We should call + // RRGetScreenResources in this case. + QScopedPointer<xcb_randr_get_screen_resources_reply_t, QScopedPointerPodDeleter> resources; + xcb_randr_get_screen_resources_current_cookie_t resourcesCookie = + xcb_randr_get_screen_resources_current(xcb_connection(), xcbScreen->root); + QScopedPointer<xcb_randr_get_screen_resources_current_reply_t, QScopedPointerPodDeleter> resources_current( + xcb_randr_get_screen_resources_current_reply(xcb_connection(), resourcesCookie, &error)); + if (!resources_current || error) { + qWarning("failed to get the current screen resources"); free(error); } else { - QScopedPointer<xcb_randr_get_screen_resources_reply_t, QScopedPointerPodDeleter> resources( - xcb_randr_get_screen_resources_reply(xcb_connection(), resourcesCookie, &error)); - if (!resources || error) { - qWarning("failed to get the screen resources"); - free(error); + xcb_timestamp_t timestamp; + xcb_randr_output_t *outputs = Q_NULLPTR; + outputCount = xcb_randr_get_screen_resources_current_outputs_length(resources_current.data()); + if (outputCount) { + timestamp = resources_current->config_timestamp; + outputs = xcb_randr_get_screen_resources_current_outputs(resources_current.data()); } else { - xcb_timestamp_t timestamp = resources->config_timestamp; - outputCount = xcb_randr_get_screen_resources_outputs_length(resources.data()); - xcb_randr_output_t *outputs = xcb_randr_get_screen_resources_outputs(resources.data()); - - for (int i = 0; i < outputCount; i++) { - QScopedPointer<xcb_randr_get_output_info_reply_t, QScopedPointerPodDeleter> output( - xcb_randr_get_output_info_reply(xcb_connection(), - xcb_randr_get_output_info_unchecked(xcb_connection(), outputs[i], timestamp), NULL)); - - // Invalid, disconnected or disabled output - if (output == NULL) - continue; - - if (output->connection != XCB_RANDR_CONNECTION_CONNECTED) { - qCDebug(lcQpaScreen, "Output %s is not connected", qPrintable( - QString::fromUtf8((const char*)xcb_randr_get_output_info_name(output.data()), - xcb_randr_get_output_info_name_length(output.data())))); - continue; - } + xcb_randr_get_screen_resources_cookie_t resourcesCookie = + xcb_randr_get_screen_resources(xcb_connection(), xcbScreen->root); + resources.reset(xcb_randr_get_screen_resources_reply(xcb_connection(), resourcesCookie, &error)); + if (!resources || error) { + qWarning("failed to get the screen resources"); + free(error); + } else { + timestamp = resources->config_timestamp; + outputCount = xcb_randr_get_screen_resources_outputs_length(resources.data()); + outputs = xcb_randr_get_screen_resources_outputs(resources.data()); + } + } - if (output->crtc == XCB_NONE) { - qCDebug(lcQpaScreen, "Output %s is not enabled", qPrintable( - QString::fromUtf8((const char*)xcb_randr_get_output_info_name(output.data()), - xcb_randr_get_output_info_name_length(output.data())))); - continue; - } + if (outputCount) { + xcb_randr_get_output_primary_cookie_t primaryCookie = + xcb_randr_get_output_primary(xcb_connection(), xcbScreen->root); + QScopedPointer<xcb_randr_get_output_primary_reply_t, QScopedPointerPodDeleter> primary( + xcb_randr_get_output_primary_reply(xcb_connection(), primaryCookie, &error)); + if (!primary || error) { + qWarning("failed to get the primary output of the screen"); + free(error); + } else { + for (int i = 0; i < outputCount; i++) { + QScopedPointer<xcb_randr_get_output_info_reply_t, QScopedPointerPodDeleter> output( + xcb_randr_get_output_info_reply(xcb_connection(), + xcb_randr_get_output_info_unchecked(xcb_connection(), outputs[i], timestamp), NULL)); + + // Invalid, disconnected or disabled output + if (output == NULL) + continue; + + if (output->connection != XCB_RANDR_CONNECTION_CONNECTED) { + qCDebug(lcQpaScreen, "Output %s is not connected", qPrintable( + QString::fromUtf8((const char*)xcb_randr_get_output_info_name(output.data()), + xcb_randr_get_output_info_name_length(output.data())))); + continue; + } + + if (output->crtc == XCB_NONE) { + qCDebug(lcQpaScreen, "Output %s is not enabled", qPrintable( + QString::fromUtf8((const char*)xcb_randr_get_output_info_name(output.data()), + xcb_randr_get_output_info_name_length(output.data())))); + continue; + } - QXcbScreen *screen = createScreen(xcbScreenNumber, xcbScreen, outputs[i], output.data()); - siblings << screen; - ++connectedOutputCount; - hasOutputs = true; - m_screens << screen; - - // There can be multiple outputs per screen, use either - // the first or an exact match. An exact match isn't - // always available if primary->output is XCB_NONE - // or currently disconnected output. - if (m_primaryScreenNumber == xcbScreenNumber) { - if (!primaryScreen || (primary && outputs[i] == primary->output)) { - if (primaryScreen) - primaryScreen->setPrimary(false); - primaryScreen = screen; - primaryScreen->setPrimary(true); - siblings.prepend(siblings.takeLast()); + QXcbScreen *screen = createScreen(xcbScreenNumber, xcbScreen, outputs[i], output.data()); + siblings << screen; + ++connectedOutputCount; + hasOutputs = true; + m_screens << screen; + + // There can be multiple outputs per screen, use either + // the first or an exact match. An exact match isn't + // always available if primary->output is XCB_NONE + // or currently disconnected output. + if (m_primaryScreenNumber == xcbScreenNumber) { + if (!primaryScreen || (primary && outputs[i] == primary->output)) { + if (primaryScreen) + primaryScreen->setPrimary(false); + primaryScreen = screen; + primaryScreen->setPrimary(true); + siblings.prepend(siblings.takeLast()); + } } } } @@ -1120,7 +1137,7 @@ void QXcbConnection::handleXcbEvent(xcb_generic_event_t *event) } } - if (!handled) + if (!handled && m_glIntegration) handled = m_glIntegration->handleXcbEvent(event, response_type); if (handled) @@ -1463,6 +1480,7 @@ static const char * xcb_atomnames = { "WM_STATE\0" "WM_CHANGE_STATE\0" "WM_CLASS\0" + "WM_NAME\0" // Session management "WM_CLIENT_LEADER\0" diff --git a/src/plugins/platforms/xcb/qxcbconnection.h b/src/plugins/platforms/xcb/qxcbconnection.h index 4c014bc6e2..1190e7c2b0 100644 --- a/src/plugins/platforms/xcb/qxcbconnection.h +++ b/src/plugins/platforms/xcb/qxcbconnection.h @@ -107,6 +107,7 @@ namespace QXcbAtom { WM_STATE, WM_CHANGE_STATE, WM_CLASS, + WM_NAME, // Session management WM_CLIENT_LEADER, diff --git a/src/plugins/platforms/xcb/qxcbcursor.cpp b/src/plugins/platforms/xcb/qxcbcursor.cpp index e3a04c1d7b..8dd27ec9c5 100644 --- a/src/plugins/platforms/xcb/qxcbcursor.cpp +++ b/src/plugins/platforms/xcb/qxcbcursor.cpp @@ -53,6 +53,12 @@ typedef int (*PtrXcursorLibrarySetTheme)(void *, const char *); typedef int (*PtrXcursorLibraryGetDefaultSize)(void *); #ifdef XCB_USE_XLIB +#include <X11/Xlib.h> +enum { + XCursorShape = CursorShape +}; +#undef CursorShape + static PtrXcursorLibraryLoadCursor ptrXcursorLibraryLoadCursor = 0; static PtrXcursorLibraryGetTheme ptrXcursorLibraryGetTheme = 0; static PtrXcursorLibrarySetTheme ptrXcursorLibrarySetTheme = 0; @@ -552,6 +558,12 @@ xcb_cursor_t QXcbCursor::createFontCursor(int cshape) } if (cursor) return cursor; + if (!cursor && cursorId) { + cursor = XCreateFontCursor(DISPLAY_FROM_XCB(this), cursorId); + if (cursor) + return cursor; + } + #endif // Non-standard X11 cursors are created from bitmaps diff --git a/src/plugins/platforms/xcb/qxcbintegration.cpp b/src/plugins/platforms/xcb/qxcbintegration.cpp index 258359d20f..2547e537a7 100644 --- a/src/plugins/platforms/xcb/qxcbintegration.cpp +++ b/src/plugins/platforms/xcb/qxcbintegration.cpp @@ -186,9 +186,9 @@ QXcbIntegration::~QXcbIntegration() QPlatformWindow *QXcbIntegration::createPlatformWindow(QWindow *window) const { + QXcbScreen *screen = static_cast<QXcbScreen *>(window->screen()->handle()); + QXcbGlIntegration *glIntegration = screen->connection()->glIntegration(); if (window->type() != Qt::Desktop) { - QXcbScreen *screen = static_cast<QXcbScreen *>(window->screen()->handle()); - QXcbGlIntegration *glIntegration = screen->connection()->glIntegration(); if (glIntegration) { QXcbWindow *xcbWindow = glIntegration->createWindow(window); xcbWindow->create(); @@ -196,7 +196,8 @@ QPlatformWindow *QXcbIntegration::createPlatformWindow(QWindow *window) const } } - Q_ASSERT(window->type() == Qt::Desktop || !window->supportsOpenGL()); + Q_ASSERT(window->type() == Qt::Desktop || !window->supportsOpenGL() + || (!glIntegration && window->surfaceType() == QSurface::RasterGLSurface)); // for VNC QXcbWindow *xcbWindow = new QXcbWindow(window); xcbWindow->create(); return xcbWindow; @@ -374,6 +375,8 @@ QVariant QXcbIntegration::styleHint(QPlatformIntegration::StyleHint hint) const // X11 always has support for windows, but the // window manager could prevent it (e.g. matchbox) return false; + case QPlatformIntegration::ReplayMousePressOutsidePopup: + return false; default: break; } diff --git a/src/plugins/platforms/xcb/qxcbwindow.cpp b/src/plugins/platforms/xcb/qxcbwindow.cpp index eabebffdab..0b38def63b 100644 --- a/src/plugins/platforms/xcb/qxcbwindow.cpp +++ b/src/plugins/platforms/xcb/qxcbwindow.cpp @@ -87,6 +87,7 @@ #include <qpa/qplatformbackingstore.h> #include <qpa/qwindowsysteminterface.h> +#include <QTextCodec> #include <stdio.h> #ifdef XCB_USE_XLIB @@ -156,6 +157,11 @@ static inline QPoint dpr_ceil(const QPoint &p, int dpr) return QPoint((p.x() + dpr - 1) / dpr, (p.y() + dpr - 1) / dpr); } +static inline QSize dpr_ceil(const QSize &s, int dpr) +{ + return QSize((s.width() + dpr - 1) / dpr, (s.height() + dpr - 1) / dpr); +} + static inline QRect mapExposeFromNative(const QRect &xRect, int dpr) { return QRect(dpr_floor(xRect.topLeft(), dpr), dpr_ceil(xRect.bottomRight(), dpr)); @@ -163,7 +169,7 @@ static inline QRect mapExposeFromNative(const QRect &xRect, int dpr) static inline QRect mapGeometryFromNative(const QRect &xRect, int dpr) { - return QRect(xRect.topLeft() / dpr, xRect.bottomRight() / dpr); + return QRect(xRect.topLeft() / dpr, dpr_ceil(xRect.size(), dpr)); } // Returns \c true if we should set WM_TRANSIENT_FOR on \a w @@ -178,8 +184,10 @@ static inline bool isTransient(const QWindow *w) || w->type() == Qt::Popup; } -static inline QImage::Format imageFormatForVisual(int depth, quint32 red_mask, quint32 blue_mask) +static inline QImage::Format imageFormatForVisual(int depth, quint32 red_mask, quint32 blue_mask, bool *rgbSwap) { + if (rgbSwap) + *rgbSwap = false; switch (depth) { case 32: if (blue_mask == 0xff) @@ -188,6 +196,11 @@ static inline QImage::Format imageFormatForVisual(int depth, quint32 red_mask, q return QImage::Format_A2BGR30_Premultiplied; if (blue_mask == 0x3ff) return QImage::Format_A2RGB30_Premultiplied; + if (red_mask == 0xff) { + if (rgbSwap) + *rgbSwap = true; + return QImage::Format_ARGB32_Premultiplied; + } break; case 30: if (red_mask == 0x3ff) @@ -198,6 +211,11 @@ static inline QImage::Format imageFormatForVisual(int depth, quint32 red_mask, q case 24: if (blue_mask == 0xff) return QImage::Format_RGB32; + if (red_mask == 0xff) { + if (rgbSwap) + *rgbSwap = true; + return QImage::Format_RGB32; + } break; case 16: if (blue_mask == 0x1f) @@ -227,6 +245,48 @@ static inline bool positionIncludesFrame(QWindow *w) return qt_window_private(w)->positionPolicy == QWindowPrivate::WindowFrameInclusive; } +#ifdef XCB_USE_XLIB +static inline XTextProperty* qstringToXTP(Display *dpy, const QString& s) +{ + #include <X11/Xatom.h> + + static XTextProperty tp = { 0, 0, 0, 0 }; + static bool free_prop = true; // we can't free tp.value in case it references + // the data of the static QByteArray below. + if (tp.value) { + if (free_prop) + XFree(tp.value); + tp.value = 0; + free_prop = true; + } + + static const QTextCodec* mapper = QTextCodec::codecForLocale(); + int errCode = 0; + if (mapper) { + QByteArray mapped = mapper->fromUnicode(s); + char* tl[2]; + tl[0] = mapped.data(); + tl[1] = 0; + errCode = XmbTextListToTextProperty(dpy, tl, 1, XStdICCTextStyle, &tp); + if (errCode < 0) + qDebug("XmbTextListToTextProperty result code %d", errCode); + } + if (!mapper || errCode < 0) { + mapper = QTextCodec::codecForName("latin1"); + if (!mapper || !mapper->canEncode(s)) + return Q_NULLPTR; + static QByteArray qcs; + qcs = s.toLatin1(); + tp.value = (uchar*)qcs.data(); + tp.encoding = XA_STRING; + tp.format = 8; + tp.nitems = qcs.length(); + free_prop = false; + } + return &tp; +} +#endif // XCB_USE_XLIB + static const char *wm_window_type_property_id = "_q_xcb_wm_window_type"; QXcbWindow::QXcbWindow(QWindow *window) @@ -292,7 +352,7 @@ void QXcbWindow::create() m_depth = platformScreen->screen()->root_depth; m_visualId = platformScreen->screen()->root_visual; const xcb_visualtype_t *visual = platformScreen->visualForId(m_visualId); - m_imageFormat = imageFormatForVisual(m_depth, visual->red_mask, visual->blue_mask); + m_imageFormat = imageFormatForVisual(m_depth, visual->red_mask, visual->blue_mask, &m_imageRgbSwap); connection()->addWindowEventListener(m_window, this); return; } @@ -364,7 +424,7 @@ void QXcbWindow::create() if (visualInfo) { m_depth = visualInfo->depth; - m_imageFormat = imageFormatForVisual(visualInfo->depth, visualInfo->red_mask, visualInfo->blue_mask); + m_imageFormat = imageFormatForVisual(visualInfo->depth, visualInfo->red_mask, visualInfo->blue_mask, &m_imageRgbSwap); Colormap cmap = XCreateColormap(DISPLAY_FROM_XCB(this), xcb_parent_id, visualInfo->visual, AllocNone); XSetWindowAttributes a; @@ -417,7 +477,7 @@ void QXcbWindow::create() } const xcb_visualtype_t *visual = platformScreen->visualForId(m_visualId); - m_imageFormat = imageFormatForVisual(m_depth, visual->red_mask, visual->blue_mask); + m_imageFormat = imageFormatForVisual(m_depth, visual->red_mask, visual->blue_mask, &m_imageRgbSwap); Q_XCB_CALL(xcb_create_window(xcb_connection(), m_depth, @@ -1407,6 +1467,12 @@ void QXcbWindow::setWindowTitle(const QString &title) 8, ba.length(), ba.constData())); + +#ifdef XCB_USE_XLIB + XTextProperty *text = qstringToXTP(DISPLAY_FROM_XCB(this), title); + if (text) + XSetWMName(DISPLAY_FROM_XCB(this), m_window, text); +#endif xcb_flush(xcb_connection()); } diff --git a/src/plugins/platforms/xcb/qxcbwindow.h b/src/plugins/platforms/xcb/qxcbwindow.h index cd3c091973..2442e6c4e3 100644 --- a/src/plugins/platforms/xcb/qxcbwindow.h +++ b/src/plugins/platforms/xcb/qxcbwindow.h @@ -114,6 +114,7 @@ public: xcb_window_t xcb_window() const { return m_window; } uint depth() const { return m_depth; } QImage::Format imageFormat() const { return m_imageFormat; } + bool imageNeedsRgbSwap() const { return m_imageRgbSwap; } bool handleGenericEvent(xcb_generic_event_t *event, long *result) Q_DECL_OVERRIDE; @@ -205,6 +206,7 @@ protected: uint m_depth; QImage::Format m_imageFormat; + bool m_imageRgbSwap; xcb_sync_int64_t m_syncValue; xcb_sync_counter_t m_syncCounter; |