无样式窗体即 WindowStyle="None"
不可改变大小即ResizeMode="NoResize"
一般为了美化窗体一般都会这么使用这两个属性,但是用了这两个属性后就会出现一些问题:
- 用cs代码来控制窗体最大化时会覆盖下方菜单栏;
- 无法移动窗体;
先来解决窗体移动的问题
前端代码:
<Window x:Class="WpfApp4.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:WpfApp4"
mc:Ignorable="d"
Title="MainWindow" Height="450" Width="800" WindowStyle="None" ResizeMode="NoResize">
<Grid >
<Grid.RowDefinitions >
<RowDefinition Height="50"></RowDefinition>
<RowDefinition></RowDefinition>
</Grid.RowDefinitions>
<Grid Background="#268E80" MouseDown="Grid_MouseDown" ></Grid>
</Grid>
</Window>
在这里我们定义了一个Grid来当做鼠标拖动的受体,也就是鼠标拖动这个grid时才能移动窗体。(PS:这个Grid必须设置背景颜色,否则无法触发点击事件,可以使用透明色Transparent)我们定义了一个鼠标点击事件。
后端代码:
private void Grid_MouseDown(object sender, MouseButtonEventArgs e)
{
if (e.LeftButton == MouseButtonState.Pressed)
{
this.DragMove();
}
}
这样就可以实现拖动窗体;
我们再来说窗体缩放的问题(最大化、正常切换)
因为使用wpf的最大化会直接遮挡下方菜单所以此处只能自己重写一下其中的逻辑。
//窗体是否最大化
Boolean isMaxed;
/// <summary>
/// 改变屏幕尺寸 最大化正常
/// </summary>
void ChengeWindowSize()
{
if (isMaxed)
{
//缩放比例0.9
this.Width = SystemParameters.WorkArea.Width * 0.9;
this.Height = SystemParameters.WorkArea.Height * 0.9;
this.Left = (SystemParameters.WorkArea.Width - this.Width) / 2;
this.Top = (SystemParameters.WorkArea.Height - this.Height) / 2;
}
else
{
this.Left = 0;
this.Top = 0;
this.Width = SystemParameters.WorkArea.Width;
this.Height = SystemParameters.WorkArea.Height;
}
isMaxed = !isMaxed;
}
如上代码可以解决,单显示器的窗体缩放问题,但是如果出现多显示器又会出现问题:
- 无法确定窗体在哪个显示器上;
- 显示器大小不一致,导致窗体不匹配;
- win10系统 自带缩放比例,会导致副屏出现尺寸问题。
(ps:这里吐槽一下,win10 缩放比例对于开发者来说真的是害人)
因为需要获取多屏幕尺寸所以先要引入动态链接库System.Windows.Forms、System.Drawing
上代码
using System;
using System.Windows;
using System.Windows.Input;
namespace WpfApp4
{
/// <summary>
/// MainWindow.xaml 的交互逻辑
/// </summary>
public partial class MainWindow : Window
{
//窗体是否最大化
Boolean isMaxed;
public MainWindow()
{
InitializeComponent();
//已开始就最大化
ChengeWindowSize();
}
/// <summary>
/// 改变屏幕尺寸 最大化正常
/// </summary>
void ChengeWindowSize()
{
//主屏宽度
var primaryScreenWidth = SystemParameters.PrimaryScreenWidth;
var primaryScreenHeight = SystemParameters.PrimaryScreenHeight;
//获取屏幕数量
int screenCount = System.Windows.Forms.Screen.AllScreens.Length;
//获取屏幕缩放比例
var scaleX = System.Windows.Forms.Screen.PrimaryScreen.Bounds.Width/ primaryScreenWidth;
var scaleY = System.Windows.Forms.Screen.PrimaryScreen.Bounds.Height / primaryScreenHeight;
//判断有几个屏幕
if (screenCount == 1)
{
//只有一个屏幕
if (isMaxed)
{
this.Width = SystemParameters.WorkArea.Width * 0.9;
this.Height = SystemParameters.WorkArea.Height * 0.9;
this.Left = (SystemParameters.WorkArea.Width - this.Width) / 2;
this.Top = (SystemParameters.WorkArea.Height - this.Height) / 2;
}
else
{
this.Left = 0;
this.Top = 0;
this.Width = SystemParameters.WorkArea.Width;
this.Height = SystemParameters.WorkArea.Height;
}
isMaxed = !isMaxed;
}
else
{
//存在多个屏幕
//判断窗体在哪个屏幕上
foreach (var screens in System.Windows.Forms.Screen.AllScreens)
{
//算出屏幕正常大小
var screenWidth = screens.WorkingArea.Width / scaleX;
var screenHeight = screens.WorkingArea.Height / scaleX;
var screenLeft = screens.Bounds.Left / scaleX;
var screenRight = screens.Bounds.Right / scaleX;
if (this.Left >= screenLeft && this.Left < screenRight) {
if (isMaxed)
{
//正常尺寸为最大尺寸的90%
this.Width = screenWidth * 0.9;
this.Height = screenHeight * 0.9;
this.Left = (screenWidth - this.Width) / 2+ screenLeft;
this.Top = (screenHeight - this.Height) / 2;
}
else
{
this.Left = screenLeft;
this.Top = 0;
this.Width = screenWidth;
this.Height = screenHeight;
}
isMaxed = !isMaxed;
return;
}
}
}
}
private void Grid_MouseDown(object sender, MouseButtonEventArgs e)
{
if (e.LeftButton == MouseButtonState.Pressed)
{
this.DragMove();
}
if (e.RightButton == MouseButtonState.Pressed)
{
ChengeWindowSize();
}
}
}
}
这样就可以解决多显示器最大化、正常尺寸之间的切换;
若有问题请指出