Reputation: 19396
I wanted to know the resolution of the screen and I have read this question:Get and Set Screen Resolution
However, it seems this give the resolution of the primary screen, but I would like to know if there is some way to get the resolution of the screen in which is shown the window.
For example, I have to screens, the laptop screen and a monitor. The laptop has a resolution of 1366x768 and the monitor has a resolution of 1920x1080. The main screen is the monitor, and the screen of the laptop is the secondary screen.
I would like to have a simple application that it has a button, and I would like than when I click the button, it gives the resolution of the monitor in which I am seeing the window. If I drag the window to the other monitor, then it should give me the resolution of the other monitor.
Thanks.
Upvotes: 0
Views: 585
Reputation: 3601
You can accomplish it by various ways but I like straightforward way using MonitorFromRect and GetMonitorInfo functions. Assuming you set proper app.manifest for Per-Monitor DPI, the following extension method will work to get screen Rect from a FrameworkElement.
Regarding the point jwdonahue raised, this method will return the Rect of screen which has the largest intersection with the specified FrameworkElement.
using System;
using System.Runtime.InteropServices;
using System.Windows;
using System.Windows.Media;
public static class ScreenHelper
{
public static Rect ToScreenRect(this FrameworkElement element) => GetMonitorRect(GetElementRect(element));
private static Rect GetElementRect(FrameworkElement element)
{
var point = element.PointToScreen(new Point(0, 0));
var dpi = VisualTreeHelper.GetDpi(element);
return new Rect(point, new Size(element.ActualWidth * dpi.DpiScaleX, element.ActualHeight * dpi.DpiScaleY));
}
private static Rect GetMonitorRect(Rect elementRect)
{
RECT rect = elementRect;
var monitorHandle = MonitorFromRect(ref rect, MONITOR_DEFAULTTONULL);
if (monitorHandle != IntPtr.Zero)
{
var monitorInfo = new MONITORINFO { cbSize = (uint)Marshal.SizeOf<MONITORINFO>() };
if (GetMonitorInfo(monitorHandle, ref monitorInfo))
{
return monitorInfo.rcMonitor;
}
}
return Rect.Empty;
}
[DllImport("User32.dll")]
private static extern IntPtr MonitorFromRect(ref RECT lprc, uint dwFlags);
private const uint MONITOR_DEFAULTTONULL = 0x00000000;
[DllImport("User32.dll")]
[return: MarshalAs(UnmanagedType.Bool)]
private static extern bool GetMonitorInfo(IntPtr hMonitor, ref MONITORINFO lpmi);
[StructLayout(LayoutKind.Sequential)]
private struct MONITORINFO
{
public uint cbSize;
public RECT rcMonitor;
public RECT rcWork;
public uint dwFlags;
}
[StructLayout(LayoutKind.Sequential)]
private struct RECT
{
public int left;
public int top;
public int right;
public int bottom;
public static implicit operator Rect(RECT rect)
{
return new Rect(
rect.left,
rect.top,
rect.right - rect.left,
rect.bottom - rect.top);
}
public static implicit operator RECT(Rect rect)
{
return new RECT
{
left = (int)rect.X,
top = (int)rect.Y,
right = (int)rect.Right,
bottom = (int)rect.Bottom
};
}
}
}
Upvotes: 1