0

I want to get the screen size of the primary screen, without adding any references (e.g. WinForms or Presentation). I found a similar question here, however there is no solution which doesn't include downloading or something like that.

But I want to make a method, which can be executed in the C# interactive on any other pc. Therefore I need a solution that doesn't reference other stuff than the standard (E.g. System, System.Core, ... is allowed).

I do know this is possible with

System.Windows.Forms.Screen.PrimaryScreen.Bounds;

but as this requires the System.Windows.Forms reference, it's not suitable for me. But basically the result of this snippet is what I want to get without references.

Community
  • 1
  • 1
MetaColon
  • 2,895
  • 3
  • 16
  • 38

3 Answers3

1

Here's an example I came up with.

I have noticed that it does not work correctly on High-DPI Screens. It will report the apparent resolution, not the actual resolution.

    static void Main(string[] args)
    {
        var size = GetScreenSize();
        Console.WriteLine(size.Length + " x " + size.Width);
        Console.ReadLine();
    }

    static Size GetScreenSize()
    {
        return new Size(GetSystemMetrics(0), GetSystemMetrics(1));
    }

    struct Size
    {
        public Size(int l, int w)
        {
            Length = l;
            Width = w;
        }

        public int Length { get; set; }
        public int Width { get; set; }
    }

    [DllImport("User32.dll", ExactSpelling = true, CharSet = CharSet.Auto)]
    public static extern int GetSystemMetrics(int nIndex);
Adam Schiavone
  • 2,412
  • 3
  • 32
  • 65
0

If you don't want to use those libraries, You'll probably need to use native methods. I can't think of a way around this, as you'll need to communicate with the system any way you go.

A good place to start would be the source of System.Windows.Forms.Screen

Here's a link to the source. I bet you could strip down their code, and get the bare minimum.

Adam Schiavone
  • 2,412
  • 3
  • 32
  • 65
  • I actually tried, but failed. Could you provide a code example to achieve this? It's okay, if some native stuff is included, I just wouldn't call myself experienced with it. – MetaColon May 02 '17 at 14:11
  • I'll give it a shot when I've got some free time (if somebody else doesn't beat me to it) It may be a few hours though, so I hope you're not in a time crunch. – Adam Schiavone May 02 '17 at 14:25
  • I'm not, so take your time :) – MetaColon May 02 '17 at 14:27
  • I actually posted a solution as well - however this one isn't very beautiful and save, so maybe you could still post an answer as well. – MetaColon May 02 '17 at 15:24
0

I actually found a solution to this:

using System;
using System.Runtime.InteropServices;
static void Main()
{
    EnumWindows(E, IntPtr.Zero);
    Console.Write($"{_.Item1}x{_.Item2}");
}


struct R
{
    int l;
    int t;
    public int r;
    public int b;

    public override string ToString() => $"{l},{t},{r},{b}";
    public bool i() => l == 0 && r != 00;
}

static (int, int) _;

static bool E(IntPtr w, IntPtr l)
{
    var r = new R();
    GetWindowRect(w, ref r);
    if (r.i() && _.Item1 == 0)
        _ = (r.r, r.b);
    return true;
}

delegate bool P(IntPtr w, IntPtr l);

[DllImport("user32.dll")]
static extern bool EnumWindows(P e, IntPtr l);

[DllImport("user32.dll")]
static extern bool GetWindowRect(IntPtr w, ref R r);
Main()

Paste this into your interactive and it should output the screen resolution - at least it does for me.

Don't ask me how it works, it's stumped together from different tutorials and pressed into the interactive. Therefore I can't guarantee this will work on every pc.

Could somebody else please test this?

MetaColon
  • 2,895
  • 3
  • 16
  • 38