summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRafael Roquetto <rafael.roquetto.qnx@kdab.com>2012-09-12 15:53:46 +0200
committerThe Qt Project <gerrit-noreply@qt-project.org>2012-09-19 19:54:44 +0200
commit89d9f8fe949e65e7455fabe288ea284aa6de06b1 (patch)
treed67be8e8812e961eeb3b06bd59f2443e048580e0
parent2794b99bc66734b6a31f99c83b593831c03be710 (diff)
Rotate non maximized windows
There are two types of rotation to be considered: 1. Rotation of native widgets The corresponding window should be rotated and resized proportionally to the new screen geometry. 2. Rotation of toplevel windows. The window will be only rotated. It will be only moved or resized if it becomes clipped, in order to be fitted on the screen properly. Change-Id: Ice92427ac07a9bea284e68917ff3e0f436722bc0 Reviewed-by: Sean Harmer <sean.harmer@kdab.com>
-rw-r--r--src/plugins/platforms/qnx/qqnxscreen.cpp112
-rw-r--r--src/plugins/platforms/qnx/qqnxscreen.h3
2 files changed, 114 insertions, 1 deletions
diff --git a/src/plugins/platforms/qnx/qqnxscreen.cpp b/src/plugins/platforms/qnx/qqnxscreen.cpp
index 95b3ef0e1e..28fce1ba46 100644
--- a/src/plugins/platforms/qnx/qqnxscreen.cpp
+++ b/src/plugins/platforms/qnx/qqnxscreen.cpp
@@ -251,6 +251,8 @@ void QQnxScreen::setRotation(int rotation)
if (m_rootWindow)
m_rootWindow->setRotation(rotation);
+ const QRect previousScreenGeometry = geometry();
+
// Swap dimensions if we've rotated 90 or 270 from initial orientation
if (isOrthogonal(m_initialRotation, rotation)) {
m_currentGeometry = QRect(0, 0, m_initialGeometry.height(), m_initialGeometry.width());
@@ -265,6 +267,9 @@ void QQnxScreen::setRotation(int rotation)
qScreenDebug() << Q_FUNC_INFO << "resize, size =" << m_currentGeometry.size();
if (m_rootWindow)
m_rootWindow->resize(m_currentGeometry.size());
+
+ if (m_primaryScreen)
+ resizeWindows(previousScreenGeometry);
} else {
// TODO: Find one global place to flush display updates
// Force immediate display update if no geometry changes required
@@ -281,7 +286,6 @@ void QQnxScreen::setRotation(int rotation)
if (m_primaryScreen) {
QWindowSystemInterface::handleScreenOrientationChange(screen(), orientation());
QWindowSystemInterface::handleScreenGeometryChange(screen(), m_currentGeometry);
- resizeMaximizedWindows();
}
// Flush everything, so that the windows rotations are applied properly.
@@ -290,6 +294,112 @@ void QQnxScreen::setRotation(int rotation)
}
}
+/*!
+ Resize the given window proportionally to the screen geometry
+*/
+void QQnxScreen::resizeNativeWidgetWindow(QQnxWindow *w, const QRect &previousScreenGeometry) const
+{
+ const qreal relativeX = static_cast<qreal>(w->geometry().topLeft().x()) / previousScreenGeometry.width();
+ const qreal relativeY = static_cast<qreal>(w->geometry().topLeft().y()) / previousScreenGeometry.height();
+ const qreal relativeWidth = static_cast<qreal>(w->geometry().width()) / previousScreenGeometry.width();
+ const qreal relativeHeight = static_cast<qreal>(w->geometry().height()) / previousScreenGeometry.height();
+
+ const QRect windowGeometry(relativeX * geometry().width(), relativeY * geometry().height(),
+ relativeWidth * geometry().width(), relativeHeight * geometry().height());
+
+ w->setGeometry(windowGeometry);
+}
+
+/*!
+ Resize the given window to fit the screen geometry
+*/
+void QQnxScreen::resizeTopLevelWindow(QQnxWindow *w, const QRect &previousScreenGeometry) const
+{
+ QRect windowGeometry = w->geometry();
+
+ const qreal relativeCenterX = static_cast<qreal>(w->geometry().center().x()) / previousScreenGeometry.width();
+ const qreal relativeCenterY = static_cast<qreal>(w->geometry().center().y()) / previousScreenGeometry.height();
+ const QPoint newCenter(relativeCenterX * geometry().width(), relativeCenterY * geometry().height());
+
+ windowGeometry.moveCenter(newCenter);
+
+ // adjust center position in case the window
+ // is clipped
+ if (!geometry().contains(windowGeometry)) {
+ const int x1 = windowGeometry.x();
+ const int y1 = windowGeometry.y();
+ const int x2 = x1 + windowGeometry.width();
+ const int y2 = y1 + windowGeometry.height();
+
+ if (x1 < 0) {
+ const int centerX = qMin(qAbs(x1) + windowGeometry.center().x(),
+ geometry().center().x());
+
+ windowGeometry.moveCenter(QPoint(centerX, windowGeometry.center().y()));
+ }
+
+ if (y1 < 0) {
+ const int centerY = qMin(qAbs(y1) + windowGeometry.center().y(),
+ geometry().center().y());
+
+ windowGeometry.moveCenter(QPoint(windowGeometry.center().x(), centerY));
+ }
+
+ if (x2 > geometry().width()) {
+ const int centerX = qMax(windowGeometry.center().x() - (x2 - geometry().width()),
+ geometry().center().x());
+
+ windowGeometry.moveCenter(QPoint(centerX, windowGeometry.center().y()));
+ }
+
+ if (y2 > geometry().height()) {
+ const int centerY = qMax(windowGeometry.center().y() - (y2 - geometry().height()),
+ geometry().center().y());
+
+ windowGeometry.moveCenter(QPoint(windowGeometry.center().x(), centerY));
+ }
+ }
+
+ // at this point, if the window is still clipped,
+ // it means that it's too big to fit on the screen,
+ // so we need to proportionally shrink it
+ if (!geometry().contains(windowGeometry)) {
+ QSize newSize = windowGeometry.size();
+ newSize.scale(geometry().size(), Qt::KeepAspectRatio);
+ windowGeometry.setSize(newSize);
+
+ if (windowGeometry.x() < 0)
+ windowGeometry.moveCenter(QPoint(geometry().center().x(), windowGeometry.center().y()));
+
+ if (windowGeometry.y() < 0)
+ windowGeometry.moveCenter(QPoint(windowGeometry.center().x(), geometry().center().y()));
+ }
+
+ w->setGeometry(windowGeometry);
+}
+
+/*!
+ Adjust windows to the new screen geometry.
+*/
+void QQnxScreen::resizeWindows(const QRect &previousScreenGeometry)
+{
+ resizeMaximizedWindows();
+
+ Q_FOREACH (QQnxWindow *w, m_childWindows) {
+
+ if (w->window()->windowState() & Qt::WindowFullScreen || w->window()->windowState() & Qt::WindowMaximized)
+ continue;
+
+ if (w->parent()) {
+ // This is a native (non-alien) widget window
+ resizeNativeWidgetWindow(w, previousScreenGeometry);
+ } else {
+ // This is a toplevel window
+ resizeTopLevelWindow(w, previousScreenGeometry);
+ }
+ }
+}
+
QQnxWindow *QQnxScreen::findWindow(screen_window_t windowHandle)
{
Q_FOREACH (QQnxWindow *window, m_childWindows) {
diff --git a/src/plugins/platforms/qnx/qqnxscreen.h b/src/plugins/platforms/qnx/qqnxscreen.h
index c2b7c68e2f..402203e7d2 100644
--- a/src/plugins/platforms/qnx/qqnxscreen.h
+++ b/src/plugins/platforms/qnx/qqnxscreen.h
@@ -106,6 +106,9 @@ private Q_SLOTS:
void keyboardHeightChanged(int height);
private:
+ void resizeNativeWidgetWindow(QQnxWindow *w, const QRect &previousScreenGeometry) const;
+ void resizeTopLevelWindow(QQnxWindow *w, const QRect &previousScreenGeometry) const;
+ void resizeWindows(const QRect &previousScreenGeometry);
void addOverlayWindow(screen_window_t window);
void removeOverlayWindow(screen_window_t window);