From 60f5e7c0eb82abd86e7eef732b3bcf41745dc331 Mon Sep 17 00:00:00 2001
From: Paul Olav Tvete <paul.tvete@theqtcompany.com>
Date: Tue, 16 Jun 2015 13:21:58 +0200
Subject: [PATCH] Scale logicalDpi when turning on screen scaling
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Assume that the logical DPI for the primary screen is sane, and
keep font sizes constant as screens are scaled. The global scale
factor will act as a zoom level, and will cause all fonts to be bigger.

Note that since we do not change logicalDpi after application startup,
the manual test sliders will not match what happens
with auto scaling. We may want to fix that...

Change-Id: I5a3daa57c2dacf0158836492d31573723e49399a
Reviewed-by: Morten Johan Sørvig <morten.sorvig@theqtcompany.com>
---
 src/gui/kernel/qhighdpiscaling.cpp               | 11 +++++++++++
 src/gui/kernel/qhighdpiscaling_p.h               |  3 +++
 src/gui/kernel/qscreen.cpp                       |  6 +++++-
 src/plugins/platforms/windows/qwindowsscreen.cpp |  8 +++-----
 4 files changed, 22 insertions(+), 6 deletions(-)

diff --git a/src/gui/kernel/qhighdpiscaling.cpp b/src/gui/kernel/qhighdpiscaling.cpp
index 2fee06c77d6..8dd6c6687d3 100644
--- a/src/gui/kernel/qhighdpiscaling.cpp
+++ b/src/gui/kernel/qhighdpiscaling.cpp
@@ -128,6 +128,7 @@ bool QHighDpiScaling::m_usePixelDensity; // use scale factor from platform plugi
 bool QHighDpiScaling::m_pixelDensityScalingActive; // pixel density scale factor > 1
 bool QHighDpiScaling::m_globalScalingActive; // global scale factor is active
 bool QHighDpiScaling::m_screenFactorSet; // QHighDpiScaling::setScreenFactor has been used
+QDpi QHighDpiScaling::m_logicalDpi; // The scaled logical DPI of the primary screen
 
 /*
     Initializes the QHighDpiScaling global variables. Called before the
@@ -159,6 +160,11 @@ void QHighDpiScaling::updateHighDpiScaling()
         }
     }
     m_active = m_globalScalingActive || m_screenFactorSet || m_pixelDensityScalingActive;
+
+    QPlatformScreen *primaryScreen = QGuiApplication::primaryScreen()->handle();
+    qreal sf = screenSubfactor(primaryScreen);
+    QDpi primaryDpi = primaryScreen->logicalDpi();
+    m_logicalDpi = QDpi(primaryDpi.first / sf, primaryDpi.second / sf);
 }
 
 /*
@@ -246,6 +252,11 @@ qreal QHighDpiScaling::screenSubfactor(const QPlatformScreen *screen)
     return factor;
 }
 
+QDpi QHighDpiScaling::logicalDpi()
+{
+    return m_logicalDpi;
+}
+
 qreal QHighDpiScaling::factor(const QScreen *screen)
 {
     // Fast path for when scaling in Qt is not used at all.
diff --git a/src/gui/kernel/qhighdpiscaling_p.h b/src/gui/kernel/qhighdpiscaling_p.h
index d60be865182..5dd9db68c4e 100644
--- a/src/gui/kernel/qhighdpiscaling_p.h
+++ b/src/gui/kernel/qhighdpiscaling_p.h
@@ -57,6 +57,7 @@ Q_DECLARE_LOGGING_CATEGORY(lcScaling);
 
 class QScreen;
 class QPlatformScreen;
+typedef QPair<qreal, qreal> QDpi;
 
 class Q_GUI_EXPORT QHighDpiScaling {
 public:
@@ -73,6 +74,7 @@ public:
     static QPoint origin(const QPlatformScreen *platformScreen);
     static QPoint mapPositionFromNative(const QPoint &pos, const QPlatformScreen *platformScreen);
     static QPoint mapPositionToNative(const QPoint &pos, const QPlatformScreen *platformScreen);
+    static QDpi logicalDpi();
 private:
     static qreal screenSubfactor(const QPlatformScreen *screen);
 
@@ -82,6 +84,7 @@ private:
     static bool m_globalScalingActive;
     static bool m_pixelDensityScalingActive;
     static bool m_screenFactorSet;
+    static QDpi m_logicalDpi;
 };
 
 // Coordinate system conversion functions:
diff --git a/src/gui/kernel/qscreen.cpp b/src/gui/kernel/qscreen.cpp
index af88a44957c..485bb983c05 100644
--- a/src/gui/kernel/qscreen.cpp
+++ b/src/gui/kernel/qscreen.cpp
@@ -235,6 +235,8 @@ qreal QScreen::physicalDotsPerInch() const
 qreal QScreen::logicalDotsPerInchX() const
 {
     Q_D(const QScreen);
+    if (QHighDpiScaling::isActive())
+        return QHighDpiScaling::logicalDpi().first;
     return d->logicalDpi.first;
 }
 
@@ -249,6 +251,8 @@ qreal QScreen::logicalDotsPerInchX() const
 qreal QScreen::logicalDotsPerInchY() const
 {
     Q_D(const QScreen);
+    if (QHighDpiScaling::isActive())
+        return QHighDpiScaling::logicalDpi().first;
     return d->logicalDpi.second;
 }
 
@@ -267,7 +271,7 @@ qreal QScreen::logicalDotsPerInchY() const
 qreal QScreen::logicalDotsPerInch() const
 {
     Q_D(const QScreen);
-    QDpi dpi = d->logicalDpi;
+    QDpi dpi = QHighDpiScaling::isActive() ? QHighDpiScaling::logicalDpi() : d->logicalDpi;
     return (dpi.first + dpi.second) * qreal(0.5);
 }
 
diff --git a/src/plugins/platforms/windows/qwindowsscreen.cpp b/src/plugins/platforms/windows/qwindowsscreen.cpp
index 7f3bb96503e..391735a0357 100644
--- a/src/plugins/platforms/windows/qwindowsscreen.cpp
+++ b/src/plugins/platforms/windows/qwindowsscreen.cpp
@@ -117,14 +117,12 @@ static bool monitorData(HMONITOR hMonitor, QWindowsScreenData *data)
         HDC hdc = CreateDC(info.szDevice, NULL, NULL, NULL);
 #endif
         if (hdc) {
-            if (!QHighDpiScaling::isActive()) { // Assume 96 DPI to get fonts right when scaling.
 #ifndef Q_OS_WINCE
-                const QDpi dpi = monitorDPI(hMonitor);
-                data->dpi = dpi.first ? dpi : deviceDPI(hdc);
+            const QDpi dpi = monitorDPI(hMonitor);
+            data->dpi = dpi.first ? dpi : deviceDPI(hdc);
 #else
-                data->dpi = deviceDPI(hdc);
+            data->dpi = deviceDPI(hdc);
 #endif
-            }
             data->depth = GetDeviceCaps(hdc, BITSPIXEL);
             data->format = data->depth == 16 ? QImage::Format_RGB16 : QImage::Format_RGB32;
             data->physicalSizeMM = QSizeF(GetDeviceCaps(hdc, HORZSIZE), GetDeviceCaps(hdc, VERTSIZE));
-- 
GitLab