如何获取所有屏幕的 DPI 比例?

2024-02-11

我需要为连接到计算机的每个屏幕(甚至那些没有打开 WPF 窗口的屏幕)获取从“控制面板”>“显示”设置的 DPI 比例。我见过很多获得 DPI 的方法(例如,http://dzimchuk.net/post/Best-way-to-get-DPI-value-in-WPF http://dzimchuk.net/post/Best-way-to-get-DPI-value-in-WPF)但这些似乎取决于Graphics.FromHwnd(IntPtr.Zero) or PresentationSource.FromVisual(visual).CompositionTarget.TransformToDevice.

有没有办法获取每个屏幕的 DPI 设置?

背景 - 我正在创建一个布局配置编辑器,以便用户可以在启动之前设置其配置。为此,我绘制了每个屏幕的相对位置。对于一种配置,我们使用具有大于默认 DPI 比例设置的 4K 显示器。与其他屏幕相比,它的绘制比实际显示的要小得多,因为它报告的分辨率与其他屏幕相同。


我找到了一种使用 WinAPI 获取 dpi 的方法。 首先需要参考System.Drawing and System.Windows.Forms。可以使用 WinAPI 从显示区域上的一点获取监视器句柄 -Screen类可以给我们这一点。然后GetDpiForMonitor函数返回指定显示器的 dpi。

public static class ScreenExtensions
{
    public static void GetDpi(this System.Windows.Forms.Screen screen, DpiType dpiType, out uint dpiX, out uint dpiY)
    {
        var pnt = new System.Drawing.Point(screen.Bounds.Left + 1, screen.Bounds.Top + 1);
        var mon = MonitorFromPoint(pnt, 2/*MONITOR_DEFAULTTONEAREST*/);
        GetDpiForMonitor(mon, dpiType, out dpiX, out dpiY);
    }

    //https://msdn.microsoft.com/en-us/library/windows/desktop/dd145062(v=vs.85).aspx
    [DllImport("User32.dll")]
    private static extern IntPtr MonitorFromPoint([In]System.Drawing.Point pt, [In]uint dwFlags);

    //https://msdn.microsoft.com/en-us/library/windows/desktop/dn280510(v=vs.85).aspx
    [DllImport("Shcore.dll")]
    private static extern IntPtr GetDpiForMonitor([In]IntPtr hmonitor, [In]DpiType dpiType, [Out]out uint dpiX, [Out]out uint dpiY);
}

//https://msdn.microsoft.com/en-us/library/windows/desktop/dn280511(v=vs.85).aspx
public enum DpiType
{
    Effective = 0,
    Angular = 1,
    Raw = 2,
}

缩放分为三种类型,您可以找到一种MSDN 中的描述 https://msdn.microsoft.com/en-us/library/windows/desktop/dn280511(v=vs.85).aspx.

我用一个新的 WPF 应用程序快速测试了它:

private void Window_Loaded(object sender, System.Windows.RoutedEventArgs e)
{
    var sb = new StringBuilder();
    sb.Append("Angular\n");
    sb.Append(string.Join("\n", Display(DpiType.Angular)));
    sb.Append("\nEffective\n");
    sb.Append(string.Join("\n", Display(DpiType.Effective)));
    sb.Append("\nRaw\n");
    sb.Append(string.Join("\n", Display(DpiType.Raw)));

    this.Content = new TextBox() { Text = sb.ToString() };
}

private IEnumerable<string> Display(DpiType type)
{
    foreach (var screen in System.Windows.Forms.Screen.AllScreens)
    {
        uint x, y;
        screen.GetDpi(type, out x, out y);
        yield return screen.DeviceName + " - dpiX=" + x + ", dpiY=" + y;
    }
}

我希望它有帮助!

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

如何获取所有屏幕的 DPI 比例? 的相关文章

随机推荐

  • 如何使用每列以前的值填充缺失的信息? [复制]

    这个问题在这里已经有答案了 可能的重复 用最新的非 NA 值替换 NA https stackoverflow com questions 7735647 replacing nas with latest non na value 如何使
  • 如何更改node.js中process.env.PORT的值?

    我想改变的值process env PORT 我怎样才能做到这一点 我运行的是 Ubuntu 12 04 仅运行一次 在 unix shell 提示符下 PORT 1234 node app js 更永久 export PORT 1234
  • 如何使用asyncio下载s3存储桶上的文件

    我使用以下代码下载 s3 存储桶中的所有文件 def main bucket name destination dir bucket boto3 resource s3 Bucket bucket name for obj in bucke
  • 在服务中运行 Android TTS

    我试图让 Android 的 TTS 在服务中运行 但我不知道为什么它不起作用 它可以编译 不会崩溃 但它就是不起作用 不过 Toast 通知确实有效 package alarm test import android app Servic
  • 我可以使用 UML 来建模网站导航吗

    我可以使用 UML 对网站导航进行建模吗 如果是的话 有人给我一些书籍 链接以供参考 网站的 UML 之类的 如果不是的话 有哪些工具可以实现这一点 基本上我是一名程序员 当我设计以前的网站时 我只是在纸上勾勒出不同的页面设计想法 然后选择
  • 运行单元测试时禁用温斯顿日志记录?

    在执行节点模块的单元测试时是否可以有选择地禁用 Winston 日志记录 理想情况下 我希望在应用程序运行时进行日志记录以提供信息和调试目的 但在运行测试时不要使演示单元测试结果混乱 我对 winston 的使用是在我的模块内部的 如下所示
  • 无法将类型 void 隐式转换为对象。 .NET MVC 部分视图结果

    我有以下控制器操作 ChildActionOnly public virtual PartialViewResult ListActions int id var actions meetingActionRepository GetAll
  • 使用 RxJava 实现存储库模式

    我正在尝试找出一种更好的方法来实现 Android 中 RxJava 中的存储库模式之类的功能 这是我到目前为止所拥有的 从here https gist github com pieces029 5e92f9003fa1a4ebc59b
  • 如何去除两个顶点之间的边?

    我想删除两个顶点之间的边 所以我在 javatinkerpop3 中的代码如下 private void removeEdgeOfTwoVertices Vertex fromV Vertex toV String edgeLabel Gr
  • 使用 IDisposable 资源进行屈服

    是否有通过可支配资源产生收益的正确方法 返回的对象是 IDisposable 但它迭代的元素是 这是一个例子 public static IEnumerable
  • JPA - 禁用 persistence.xml 的验证

    我正在迈出使用 JPA Hibernate 的第一步 总体思路是连接到遗留数据库来执行复杂的查询 我认为 hibernate 是完成这项任务的绝佳伴侣 但是 首先 我创建了一个 bean persistence xml 和 hibernat
  • 更改文本文件编码

    如何通过代码更改文本文件编码 我正在使用此代码实际创建文件本身 但如何更改编码 更改为 UTF 8 w o BOM string path E Test Example txt if File Exists path File Create
  • Visual Studio XML 文件编辑器小写

    我正在 Visual Studio 中编辑 cshtml 带有 cshtml 文件扩展名 我自动设置格式或粘贴一些 xml 这会触发自动格式 并且 Visual Studio 会小写所有 xml 属性 因此 theAttribute gt
  • Windows 终端中的 Git Bash 在单独的窗口中打开

    我想将 git bash 添加到 Windows 终端 但是 当我在终端中添加新的 git bash 选项卡时 git bash 将在另一个窗口中打开 这是我的配置 guid acrylicOpacity 0 75 closeOnExit
  • "Hello" |> printfn 在 F# 中生成错误

    https tryfsharp fsbolero io https tryfsharp fsbolero io printfn Hello 但是 使用管道运算符可以按预期工作 没有错误 Hello gt printfn 类型 string
  • Xcode 8 AppStore 上传(错误 434)

    当我尝试验证App Store构建使用Xcode 8我收到以下错误 ITunesSoftwareServiceAuthenticationErrorDomain 434 这是什么意思 我多次尝试收到相同的错误 我做了一些更改 对配置文件等
  • 使用Java读取MySQL二进制(16) UUID

    这应该是一个非常简单的问题 我只是在这里遗漏了一些基本的东西 我正在经历 那些日子之一 无法使用 Hibernate 或其他 ORM 使用 Java 准备语句 MySQL 的东西 CREATE TABLE article articleID
  • 使用 ggplot 在背景图像上绘制数据

    我正在尝试在背景图像上绘制一些数据 问题是两个层最终都使用相同的比例 不幸的是 这是有问题的 一个例子 我想绘制一些数据image https dl dropboxusercontent com u 39251 image jpg 正确的
  • java.lang.IllegalStateException:不在主线程上

    当服务器端制造商的表中没有可用数据并且数据对象为空时 我试图从 FragmentActivity 地图中的 Goolge 地图中删除标记 但我收到以下错误 我该如何修复它 Error 07 12 20 53 05 697 E Android
  • 如何获取所有屏幕的 DPI 比例?

    我需要为连接到计算机的每个屏幕 甚至那些没有打开 WPF 窗口的屏幕 获取从 控制面板 gt 显示 设置的 DPI 比例 我见过很多获得 DPI 的方法 例如 http dzimchuk net post Best way to get D