Fix the qscreen manual test for separate X screens

It is fully possible to show a window on all the connected screens
even when the screens are not virtual siblings, i.e. they do not
form one big desktop. When X is configured to use a separate screen
for each physical screen, it becomes essential to do setScreen()
either directly or via QDesktopWidget in case of widgets. The original
code attempting to call QWindow::setScreen() cannot succeed since there
is no QWindow available before the widget is shown. This is easy to
work around.

The app now works identically in all cases.

Change-Id: I519ca0c0109c68aac2f2d4e6972d14b55767b403
Reviewed-by: Gunnar Sletta <gunnar@sletta.org>
bb10
Laszlo Agocs 2015-05-07 18:05:00 +02:00
parent 1adedb7baa
commit d33edcfe37
2 changed files with 14 additions and 19 deletions

View File

@ -20,14 +20,10 @@ create two windows, and will center one each screen, by setting the geometry.
Alternatively you can configure xorg.conf to create separate screens for each
graphics card; then the mouse cursor can move between the screens, but
application windows cannot: each app needs to be started up on the screen that
you want to run it on. In either case, ideally this test app ought to create
two windows, one on each screen; but in fact, it can do that only if the
screens are virtual siblings. If they are on different Displays, the second
Display is not accessible to the QXcbConnection instance which was createad on
the first Display. It can be considered a known bug that the API appears to
make this possible (you would think QWindow::setScreen might work) but it
isn't possible.
application windows cannot: each app needs to be started on the screen that
you want to run it on (by specifying e.g. DISPLAY=:0.1 for the second screen),
or the application has to set the desired screen via QWindow::setScreen() before
showing the window.
The physical size of the screen is considered to be a constant. This can create
discrepancies in DPI when orientation is changed, or when the screen is

View File

@ -38,6 +38,7 @@
#include <QDebug>
#include <QFormLayout>
#include <QLineEdit>
#include <QDesktopWidget>
int i = 0;
@ -66,19 +67,17 @@ void screenAdded(QScreen* screen)
w->layout()->insertRow(0, "virtualSiblings", siblingsField);
updateSiblings(w);
// This doesn't work. If the multiple screens are part of
// a virtual desktop (i.e. they are virtual siblings), then
// setScreen has no effect, and we need the code below to
// change the window geometry. If on the other hand the
// screens are really separate, so that windows are not
// portable between them, XCreateWindow needs to have not just
// a different root Window but also a different Display, in order to
// put the window on the other screen. That would require a
// different QXcbConnection. So this setScreen call doesn't seem useful.
//w->windowHandle()->setScreen(screen);
// Set the screen via QDesktopWidget. This corresponds to setScreen() for the underlying
// QWindow. This is essential when having separate X screens since the the positioning below is
// not sufficient to get the windows show up on the desired screen.
QList<QScreen *> screens = QGuiApplication::screens();
int screenNumber = screens.indexOf(screen);
Q_ASSERT(screenNumber >= 0);
w->setParent(qApp->desktop()->screen(screenNumber));
// But this works as long as the screens are all virtual siblings
w->show();
// Position the windows so that they end up at the center of the corresponding screen.
QRect geom = w->geometry();
geom.setSize(w->sizeHint());
if (geom.height() > screen->geometry().height())