summaryrefslogtreecommitdiffstats
path: root/src/plugins/platforms/xcb
diff options
context:
space:
mode:
authorLiang Qi <liang.qi@theqtcompany.com>2015-03-24 07:37:43 +0100
committerLiang Qi <liang.qi@theqtcompany.com>2015-03-24 07:38:02 +0100
commit135ebe4f3d268121047fdbfee49f2dd52006165e (patch)
tree6b303103f36e69e29cfa860b8b7afc584c55d6f3 /src/plugins/platforms/xcb
parente7feb956280105113b3e58f12e5f32f54199a95a (diff)
parent1e8f50a8d069c97ea6a4f00d664c12e594884f54 (diff)
Merge remote-tracking branch 'origin/5.5' into dev
Diffstat (limited to 'src/plugins/platforms/xcb')
-rw-r--r--src/plugins/platforms/xcb/gl_integrations/gl_integrations.pro2
-rw-r--r--src/plugins/platforms/xcb/qxcbconnection.cpp26
-rw-r--r--src/plugins/platforms/xcb/qxcbwindow.cpp19
3 files changed, 39 insertions, 8 deletions
diff --git a/src/plugins/platforms/xcb/gl_integrations/gl_integrations.pro b/src/plugins/platforms/xcb/gl_integrations/gl_integrations.pro
index 29fddeabd4..29b6d1d2f7 100644
--- a/src/plugins/platforms/xcb/gl_integrations/gl_integrations.pro
+++ b/src/plugins/platforms/xcb/gl_integrations/gl_integrations.pro
@@ -4,6 +4,6 @@ contains(QT_CONFIG, egl):contains(QT_CONFIG, egl_x11) {
SUBDIRS += xcb_egl
}
-contains(QT_CONFIG, xcb-xlib):!contains(QT_CONFIG, opengles2) {
+contains(QT_CONFIG, xcb-xlib): contains(QT_CONFIG, opengl): !contains(QT_CONFIG, opengles2) {
SUBDIRS += xcb_glx
}
diff --git a/src/plugins/platforms/xcb/qxcbconnection.cpp b/src/plugins/platforms/xcb/qxcbconnection.cpp
index 11ff313144..0ca141526e 100644
--- a/src/plugins/platforms/xcb/qxcbconnection.cpp
+++ b/src/plugins/platforms/xcb/qxcbconnection.cpp
@@ -231,9 +231,8 @@ void QXcbConnection::updateScreens(const xcb_randr_notify_event_t *event)
QXcbIntegration::instance()->destroyScreen(screen);
- // QTBUG-40174, QTBUG-42985: If there are no outputs, then there must be
- // no QScreen instances; a Qt application can survive this situation, and
- // start rendering again later when there is a screen again.
+ // QTBUG-40174, QTBUG-42985: If all screens are removed, wait
+ // and start rendering again later if a screen becomes available.
} else if (!screen && output.connection == XCB_RANDR_CONNECTION_CONNECTED) {
// New XRandR output is available and it's enabled
@@ -293,13 +292,15 @@ void QXcbConnection::initializeScreens()
{
xcb_screen_iterator_t it = xcb_setup_roots_iterator(m_setup);
int xcbScreenNumber = 0; // screen number in the xcb sense
- QXcbScreen* primaryScreen = NULL;
+ QXcbScreen* primaryScreen = Q_NULLPTR;
+ xcb_screen_t *xcbScreen = Q_NULLPTR;
+ bool hasOutputs = false;
while (it.rem) {
// Each "screen" in xcb terminology is a virtual desktop,
// potentially a collection of separate juxtaposed monitors.
// But we want a separate QScreen for each output (e.g. DVI-I-1, VGA-1, etc.)
// which will become virtual siblings.
- xcb_screen_t *xcbScreen = it.data;
+ xcbScreen = it.data;
QList<QPlatformScreen *> siblings;
int outputCount = 0;
int connectedOutputCount = 0;
@@ -356,6 +357,7 @@ void QXcbConnection::initializeScreens()
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
@@ -381,6 +383,20 @@ void QXcbConnection::initializeScreens()
++xcbScreenNumber;
} // for each xcb screen
+ // If there's no randr extension, or there was some error above, or we found a
+ // screen which doesn't have outputs for some other reason (e.g. on VNC or ssh -X),
+ // but the dimensions are known anyway, and we don't already have any lingering
+ // (possibly disconnected) screens, then showing windows should be possible,
+ // so create one screen. (QTBUG-31389)
+ if (xcbScreen && !hasOutputs && xcbScreen->width_in_pixels > 0 && xcbScreen->height_in_pixels > 0 && m_screens.isEmpty()) {
+ QXcbScreen *screen = createScreen(0, xcbScreen, 0, Q_NULLPTR);
+ screen->setVirtualSiblings(QList<QPlatformScreen *>() << screen);
+ m_screens << screen;
+ primaryScreen = screen;
+ primaryScreen->setPrimary(true);
+ qCDebug(lcQpaScreen) << "found a screen with zero outputs" << screen;
+ }
+
// Ensure the primary screen is first in the list
if (primaryScreen) {
Q_ASSERT(!m_screens.isEmpty());
diff --git a/src/plugins/platforms/xcb/qxcbwindow.cpp b/src/plugins/platforms/xcb/qxcbwindow.cpp
index 0dde679a7a..eabebffdab 100644
--- a/src/plugins/platforms/xcb/qxcbwindow.cpp
+++ b/src/plugins/platforms/xcb/qxcbwindow.cpp
@@ -319,6 +319,12 @@ void QXcbWindow::create()
// currently no way to implement it for frame-exclusive geometries.
QRect rect = window()->geometry();
QPlatformWindow::setGeometry(rect);
+ QXcbScreen *currentScreen = xcbScreen();
+ QPlatformScreen *newScreen = screenForGeometry(rect);
+
+ if (newScreen != currentScreen)
+ QWindowSystemInterface::handleWindowScreenChanged(window(), newScreen->screen());
+
const int dpr = int(devicePixelRatio());
QSize minimumSize = window()->minimumSize();
@@ -583,9 +589,18 @@ void QXcbWindow::setGeometry(const QRect &rect)
propagateSizeHints();
- const QRect xRect = mapToNative(rect, int(devicePixelRatio()));
+ QXcbScreen *currentScreen = xcbScreen();
+ QPlatformScreen *newScreen = screenForGeometry(rect);
+ if (!newScreen)
+ newScreen = currentScreen;
+
+ const QRect xRect = mapToNative(rect, int(newScreen->devicePixelRatio()));
const QRect wmGeometry = windowToWmGeometry(xRect);
+
+ if (newScreen != currentScreen)
+ QWindowSystemInterface::handleWindowScreenChanged(window(), newScreen->screen());
+
if (qt_window_private(window())->positionAutomatic) {
const quint32 mask = XCB_CONFIG_WINDOW_WIDTH | XCB_CONFIG_WINDOW_HEIGHT;
const qint32 values[] = {
@@ -1919,7 +1934,7 @@ void QXcbWindow::handleConfigureNotifyEvent(const xcb_configure_notify_event_t *
if (newScreen != screen()) {
if (newScreen)
QWindowSystemInterface::handleWindowScreenChanged(window(), newScreen->screen());
- int newDpr = devicePixelRatio();
+ int newDpr = newScreen->devicePixelRatio();
if (newDpr != dpr) {
QRect newRect = mapGeometryFromNative(nativeRect, newDpr);
QPlatformWindow::setGeometry(newRect);