tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

commit 71f243cfd9ed706a19f89755e2f40b3be68424b4
parent ae425b2a55b4dd05374fbdcb80e09a19d1caa3e8
Author: Emilio Cobos Álvarez <emilio@crisal.io>
Date:   Wed, 22 Oct 2025 11:00:57 +0000

Bug 1995498 - Assume per-monitor DPI awareness. r=win-reviewers,gstoll

This should be fine on Win10+ which is all we support.

Differential Revision: https://phabricator.services.mozilla.com/D269342

Diffstat:
Mwidget/windows/ScreenHelperWin.cpp | 7+------
Mwidget/windows/WinUtils.cpp | 57++++++++-------------------------------------------------
Mwidget/windows/WinUtils.h | 1-
Mwidget/windows/nsWindow.cpp | 22++++++++++------------
Mwidget/windows/nsWindow.h | 7-------
5 files changed, 19 insertions(+), 75 deletions(-)

diff --git a/widget/windows/ScreenHelperWin.cpp b/widget/windows/ScreenHelperWin.cpp @@ -94,12 +94,7 @@ BOOL CALLBACK CollectMonitors(HMONITOR aMon, HDC, LPRECT, LPARAM ioParam) { } double scale = WinUtils::LogToPhysFactor(aMon); - DesktopToLayoutDeviceScale contentsScaleFactor; - if (WinUtils::IsPerMonitorDPIAware()) { - contentsScaleFactor.scale = 1.0; - } else { - contentsScaleFactor.scale = scale; - } + DesktopToLayoutDeviceScale contentsScaleFactor(1.0); CSSToLayoutDeviceScale defaultCssScaleFactor(scale); LayoutDeviceIntRect rect(info.rcMonitor.left, info.rcMonitor.top, info.rcMonitor.right - info.rcMonitor.left, diff --git a/widget/windows/WinUtils.cpp b/widget/windows/WinUtils.cpp @@ -234,48 +234,12 @@ float WinUtils::SystemDPI() { // static double WinUtils::SystemScaleFactor() { return SystemDPI() / 96.0; } -typedef HRESULT(WINAPI* GETDPIFORMONITORPROC)(HMONITOR, MONITOR_DPI_TYPE, UINT*, - UINT*); - -typedef HRESULT(WINAPI* GETPROCESSDPIAWARENESSPROC)(HANDLE, - PROCESS_DPI_AWARENESS*); - -GETDPIFORMONITORPROC sGetDpiForMonitor; -GETPROCESSDPIAWARENESSPROC sGetProcessDpiAwareness; - -static bool SlowIsPerMonitorDPIAware() { - // Intentionally leak the handle. - HMODULE shcore = LoadLibraryEx(L"shcore", NULL, LOAD_LIBRARY_SEARCH_SYSTEM32); - if (shcore) { - sGetDpiForMonitor = - (GETDPIFORMONITORPROC)GetProcAddress(shcore, "GetDpiForMonitor"); - sGetProcessDpiAwareness = (GETPROCESSDPIAWARENESSPROC)GetProcAddress( - shcore, "GetProcessDpiAwareness"); - } - PROCESS_DPI_AWARENESS dpiAwareness; - return sGetDpiForMonitor && sGetProcessDpiAwareness && - SUCCEEDED( - sGetProcessDpiAwareness(GetCurrentProcess(), &dpiAwareness)) && - dpiAwareness == PROCESS_PER_MONITOR_DPI_AWARE; -} - -/* static */ -bool WinUtils::IsPerMonitorDPIAware() { - static bool perMonitorDPIAware = SlowIsPerMonitorDPIAware(); - return perMonitorDPIAware; -} - /* static */ float WinUtils::MonitorDPI(HMONITOR aMonitor) { - if (IsPerMonitorDPIAware()) { - UINT dpiX, dpiY = 96; - sGetDpiForMonitor(aMonitor ? aMonitor : GetPrimaryMonitor(), - MDT_EFFECTIVE_DPI, &dpiX, &dpiY); - return dpiY; - } - - // We're not per-monitor aware, use system DPI instead. - return SystemDPI(); + UINT dpiX, dpiY = 96; + GetDpiForMonitor(aMonitor ? aMonitor : GetPrimaryMonitor(), MDT_EFFECTIVE_DPI, + &dpiX, &dpiY); + return dpiY; } /* static */ @@ -316,14 +280,9 @@ WinUtils::GetPrimaryMonitor() { /* static */ HMONITOR WinUtils::MonitorFromRect(const gfx::Rect& rect) { - // convert coordinates from desktop to device pixels for MonitorFromRect - double dpiScale = - IsPerMonitorDPIAware() ? 1.0 : LogToPhysFactor(GetPrimaryMonitor()); - - RECT globalWindowBounds = {NSToIntRound(dpiScale * rect.X()), - NSToIntRound(dpiScale * rect.Y()), - NSToIntRound(dpiScale * (rect.XMost())), - NSToIntRound(dpiScale * (rect.YMost()))}; + RECT globalWindowBounds = {NSToIntRound(rect.X()), NSToIntRound(rect.Y()), + NSToIntRound(rect.XMost()), + NSToIntRound(rect.YMost())}; return ::MonitorFromRect(&globalWindowBounds, MONITOR_DEFAULTTONEAREST); } @@ -340,7 +299,7 @@ int WinUtils::GetSystemMetricsForDpi(int nIndex, UINT dpi) { if (HasSystemMetricsForDpi()) { return sGetSystemMetricsForDpi(nIndex, dpi); } else { - double scale = IsPerMonitorDPIAware() ? dpi / SystemDPI() : 1.0; + double scale = dpi / SystemDPI(); return NSToIntRound(::GetSystemMetrics(nIndex) * scale); } } diff --git a/widget/windows/WinUtils.h b/widget/windows/WinUtils.h @@ -217,7 +217,6 @@ class WinUtils { */ static double SystemScaleFactor(); - static bool IsPerMonitorDPIAware(); /** * Get the DPI of the given monitor if it's per-monitor DPI aware, otherwise * return the system DPI. diff --git a/widget/windows/nsWindow.cpp b/widget/windows/nsWindow.cpp @@ -5518,18 +5518,16 @@ bool nsWindow::ProcessMessageInternal(UINT msg, WPARAM& wParam, LPARAM& lParam, case WM_MOVING: FinishLiveResizing(MOVING); - if (WinUtils::IsPerMonitorDPIAware()) { - // Sometimes, we appear to miss a WM_DPICHANGED message while moving - // a window around. Therefore, call ChangedDPI and ResetLayout here - // if it appears that the window's scaling is not what we expect. - // This causes the prescontext and appshell window management code to - // check the appUnitsPerDevPixel value and current widget size, and - // refresh them if necessary. If nothing has changed, these calls will - // return without actually triggering any extra reflow or painting. - if (WinUtils::LogToPhysFactor(mWnd) != mDefaultScale) { - ChangedDPI(); - ResetLayout(); - } + // Sometimes, we appear to miss a WM_DPICHANGED message while moving + // a window around. Therefore, call ChangedDPI and ResetLayout here + // if it appears that the window's scaling is not what we expect. + // This causes the prescontext and appshell window management code to + // check the appUnitsPerDevPixel value and current widget size, and + // refresh them if necessary. If nothing has changed, these calls will + // return without actually triggering any extra reflow or painting. + if (WinUtils::LogToPhysFactor(mWnd) != mDefaultScale) { + ChangedDPI(); + ResetLayout(); } break; diff --git a/widget/windows/nsWindow.h b/widget/windows/nsWindow.h @@ -196,13 +196,6 @@ class nsWindow final : public nsIWidget { double GetDefaultScaleInternal() override; void DidClearParent(nsIWidget* aOldParent) override; int32_t LogToPhys(double aValue); - mozilla::DesktopToLayoutDeviceScale GetDesktopToDeviceScale() override { - if (mozilla::widget::WinUtils::IsPerMonitorDPIAware()) { - return mozilla::DesktopToLayoutDeviceScale(1.0); - } else { - return mozilla::DesktopToLayoutDeviceScale(GetDefaultScaleInternal()); - } - } void Show(bool aState) override; bool IsVisible() const override;