获取屏幕的本机分辨率

9

有没有一种方法可以在C#中获取屏幕的本机分辨率?

我之所以问这个问题,是因为我有一些曲线,无论分辨率如何,它们看起来都非常重要。当屏幕不处于本机分辨率时,它们看起来与以前有些不同,我想显示一个警告说明情况。


当你绘制曲线时,需要考虑纵横比。 - Moo-Juice
C# 不是关键,你使用的是 .NET 并且要么用 WinForms 要么用 WPF。 - H H
好的,抱歉,我正在使用带有WPF的.NET。 - Mathias
5
我猜你指的是LCD屏幕的固有分辨率。最合理的假设是用户选择了与LCD面板分辨率匹配的视频适配器分辨率。如果没有匹配,那么显示效果总是很差,编写处理错误的代码并不是非常有用。如果你真的想深入研究这个问题,那么你需要使用WMI做些什么。 - Hans Passant
在这种情况下,用户有时会使用与本机分辨率不同的其他分辨率。我需要创建一个警告,告知他们由于分辨率的原因,曲线可能看起来略有不同。并非所有用户都是最懂计算机的人。不过我会研究一下 WMI 的事情。 - Mathias
1
你如何希望一个没有经验的用户对这样的消息做出反应?他完全不知道你在说什么。 - Hans Passant
4个回答

5

根据我的经验,最好的解决方案是从显示器的EDID中提取信息。

如何获取本机分辨率的答案在这里:如何通过VB6.0从EDID文件中获取连接的显示器的本机分辨率?

我编写了一个小的JavaScript代码,可以从从第54个字节开始的8个字节中获取分辨率。

var dtd = 0;
var edid =  new Uint8Array(8);
var i = 0;

edid[i++] = 0x0E;
edid[i++] = 0x1F;
edid[i++] = 0x00;
edid[i++] = 0x80;
edid[i++] = 0x51;
edid[i++] = 0x00;
edid[i++] = 0x1B;
edid[i++] = 0x30;

var horizontalRes = ((edid[dtd+4] >> 4) << 8) | edid[dtd+2] ;
var verticalRes = ((edid[dtd+7] >> 4) << 8) | edid[dtd+5];
console.log(horizontalRes+", "+verticalRes);

这里是C#版本:

    static Point ExtractResolution(byte [] edid)
    {
        const int dtd = 54;
        var horizontalRes = ((edid[dtd + 4] >> 4) << 8) | edid[dtd + 2];
        var verticalRes = ((edid[dtd + 7] >> 4) << 8) | edid[dtd + 5];
        return new Point(horizontalRes, verticalRes);
    }

4

通常情况下,最大分辨率是液晶显示器的原生分辨率。但并非总是如此。如果我们能利用它,获得最大分辨率就足够了。

可以通过以下方式获取最大分辨率:

    [DllImport("user32.dll")]
    private static extern int EnumDisplaySettings(string deviceName, int modeNum, ref DeviceMode devMode);

    /// <summary>
    /// Gets the max resolution + refresh rate supported by specific display
    /// </summary>
    /// <param name="deviceName">Device name(System.Windows.Forms.Screen.DeviceName)</param>
    /// <param name="dispWidth">Width of the display</param>
    /// <param name="dispHeight">Height of the display</param>
    /// <param name="refreshRate">Refresh rate of the display</param>
    /// <returns></returns>
    public static void GetMaxResolutionWithRefreshRate(string deviceName, out int dispWidth, out int dispHeight, out int refreshRate)
    {
        dispWidth = dispHeight = refreshRate = 0;
        DeviceMode deviceMode = new DeviceMode();
        for (int i = 0; Win32.EnumDisplaySettings(deviceName, i, ref deviceMode) != 0; i++)
        {
            if (deviceMode.dmPelsWidth > dispWidth || (deviceMode.dmPelsWidth == dispWidth && deviceMode.dmPelsHeight >= dispHeight && deviceMode.dmDisplayFrequency >= refreshRate))
            {
                dispWidth = deviceMode.dmPelsWidth;
                dispHeight = deviceMode.dmPelsHeight;
                refreshRate = deviceMode.dmDisplayFrequency;
            }
        }
    }

public static void GetMaxResolutionWithRefreshRate(out int dispWidth, out int dispHeight, out int refreshRate)
    {
        GetMaxResolutionWithRefreshRate(null, out dispWidth, out dispHeight, out refreshRate);
    }

2

试试这样做:

GraphicsAdapter.DefaultAdapter.CurrentDisplayMode.Width
GraphicsAdapter.DefaultAdapter.CurrentDisplayMode.Height

要获取屏幕的当前分辨率,您可以使用以下代码:-
Rectangle resolution = Screen.PrimaryScreen.Bounds;

现在让我们来改变分辨率。

请查看这个链接

Screen screen = Screen.PrimaryScreen;
int S_width=screen.Bounds.Width;
int S_height=screen.Bounds.Height;

我的苹果Macbook Retina的本机分辨率为2880x1800。我已在分辨率设置中选择了它。然而,由于Windows进行了缩放,因为它是高DPI,Screen class告诉我分辨率为1440x900。问题是DWM也说DPI为96,在大多数情况下这很好,但如果您需要知道本机分辨率,则Screen无法帮助您。 - The Muffin Man

2
在WinForms中,您可以使用以下之一:
var someScreen = Screen.AllScreens[i];
var mainScreen = Screen.PrimaryScreen;

屏幕有一个范围(总体)和一个工作区(净)的矩形。

再次考虑,这只会告诉您当前分辨率。不过,正如已经评论的那样,您确实想知道宽高比。


这只是当前分辨率吗?如果存在的话,我想知道该屏幕的推荐分辨率(LCD屏幕的实际像素数)。 - Mathias
@Mathias - 请查看此链接:http://bytes.com/topic/c-sharp/answers/821321-there-any-way-get-monitor-native-resolution。 "一些显示器有本地分辨率,而有些则没有。如果是液晶显示器,则本地分辨率是其支持的最高分辨率。如果是CRT显示器,则它没有本地分辨率。" - Corak
是的,你只能获取“当前”的分辨率。你确定你有责任检测不同的设置吗?听起来像是功能膨胀。 - H H

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接