我一直试图让我的WPF应用程序跨越多个显示器一段时间,并且几乎让它工作。
当我设置以下行时似乎出现了问题:
win1.WindowState = WindowState.Maximized
这会导致应用程序仅跨越主屏幕。
我的代码如下:
public partial class App : Application
{
private void Application_Startup(object sender, StartupEventArgs e)
{
Window1 win1 = new Window1();
win1.WindowStartupLocation = WindowStartupLocation.Manual;
win1.Width = 2560;
win1.Height = 1024;
win1.Left = 0;
win1.Top = 0;
win1.Topmost = true;
win1.Background = new SolidColorBrush(Colors.Black);
win1.WindowStyle = WindowStyle.None;
win1.Show();
win1.Focus();
}
}
在窗口1内:
public partial class Window1 : Window
{
public Window1()
{
}
private void Window_Loaded(object sender, RoutedEventArgs e)
{
WindowState = WindowState.Maximized;
}
}
此示例有效,但窗口未最大化,应用程序边框仍然可见。
在Application_Startup中包含最大化减速度使监视器最大化到主监视器。
为什么会这样?
答案 0 :(得分:11)
首先请注意,“最大化”的概念与单个监视器相关联,因此您无法在多个监视器上真正拥有最大化窗口。当然在WPF中,您可以创建自己的窗口框架并在其中绘制任何您喜欢的内容,因此如果您需要,您当然可以让用户认为窗口最大化并跨越多个屏幕。
另请注意,只有两种情况可以跨越两个带有单个矩形窗口的监视器:
否则,您将需要使用两个单独的窗口来覆盖两个监视器的整个表面,或使用包含任何监视器未覆盖的区域的大窗口。
好的,这里是如何获取定位窗口所需的信息:
WPF本身并未提供询问您的显示器数量,分辨率或相对位置的方法。幸运的是,我们可以使用[DllImport]直接调用Win32。要获得显示器分辨率和布局,只需:
这是基本的想法:
List<MONITORINFO> GetAllMonitorInfo()
{
var result = List<MONITORINFO>();
EnumDisplayMonitors(null, null,
(hMonitor, hdcMonitor, lprcMonitor, dwData) =>
{
var info = new MONITORINFO { cbSize = Marshall.Sizeof(typeof(MONITORINFO)) };
GetMonitorInfo(hMonitor, ref info);
result.Add(info);
}, null);
return result;
}
获得显示器坐标后,使用您选择的算法选择要创建的窗口数以及每个窗口所需的坐标。然后使用显式大小和位置创建窗口。
请注意,您可能希望使用rcWork而不是rcMonitor,因此您不会覆盖开始菜单等。
另请注意,在许多情况下,返回的某些坐标将为负数,例如,如果辅助监视器位于主监视器的左侧。这不是问题:只需使用给定的坐标,您的窗口就会显示在正确的位置。
答案 1 :(得分:-1)
如果您始终可以假设您的辅助显示器与主显示器的分辨率相同,则可以实现以下内容:
// Use this is you are concerned about the taskbar height Rect workArea = SystemParameters.WorkArea; this.Width = SystemParameters.PrimaryScreenWidth * 2; this.Height = workArea.Bottom; this.Left = 0; this.Top = 0;
或者:
// Use this is you don't care about the taskbar height this.Width = SystemParameters.PrimaryScreenWidth * 2; this.Height = SystemParameters.PrimaryScreenHeight; this.Left = 0; this.Top = 0;