Windows 8.1中的TransformToDevice转换是否随DPI设置而变化?

时间:2013-11-20 15:08:58

标签: c# wpf dpi

我已经构建了一个WPF应用程序,它有一个可以停靠在桌面边缘的窗口。我使用SHAppBarMessage WIN32 API来执行对接功能。

在Windows 8.1下,我注意到停靠时,窗口只保留了所需宽度的一半。我的代码从停靠的窗口获取PresentationSource对象,然后获取TransformToDevice Matrix对象:

PresentationSource source = PresentationSource.FromVisual( window );
Matrix TransformToDevice = source.CompositionTarget.TransformToDevice;

然后我使用Matrix将窗口的ActualHeightActualWidth转换为设备坐标,然后计算桌面上区域的大小以保留窗口:

Size windowSize = (Size) source.CompositionTarget.TransformToDevice.Transform( new Vector( appbarWindow.ActualWidth, appbarWindow.ActualHeight ) );

只要显示器处于100%DPI模式,所有这些代码都有效,但更改DPI设置时问题会出现。在较高的DPI设置(即DPI> 100%)中,为桌面上的窗口保留的区域比窗口窄。

在我的调试中,我在计算上面窗口大小的行上放置了一个断点。我发现在100%DPI设置中,变换Matrix是Identity矩阵。但是在更改DPI设置后,Matrix保持不变!

我认为如果DPI设置发生变化,这个变换矩阵会改变吗?如果他们不这样做,我如何获得使DPI设置生效的转换?当DPI设置改变时,我应该调用一种方法吗?如果是这样,我如何获得DPI设置更改的通知?我有引发SystemEvents.DisplaySettingsChanged事件时调用的代码,并且在DPI设置更改时调用它。但转换始终是Identity Matrix。他们不应该改变吗?如何获得正确的变换矩阵?

1 个答案:

答案 0 :(得分:0)

我发现对我的问题的简短回答是“不”。 Windows 8.1增加了一种称为每监视器DPI感知的新型DPI感知。 WPF代码不是每个监视器DPI感知。事实证明,您必须处理每个监视器的DPI感知,这与WPF内置的系统DPI感知不同。