在C#程序开发中,Form的size和top,left通常是绝对的,不管怎么拖动调整Form的大小,其空间都不会发生变化。这中状态不符合日常见到的软件的风格,正常的软件,控件的大小是可以跟随窗口大小的变化而变化的。实现这样的功能有两种方式:
1、设置每一个空间的Anchor属性都为Top, Bottom, Left, Right,也就是将红框中十字架的每一个都点选上。此外还有Dock属性可以设置(强制设置控件与父空间的边缘关系,如贴近父控件的上左边,更多可以参考https://blog.csdn.net/qq_41867007/article/details/122513283)
2、监听From的resize事件,在窗体resize时同时修改控件的size信息(也就是width、height)和location信息(也就是top、left)。先存储原始窗体中的所有控件的size信息和location信息,在窗体大小发生变化时计算出new_size相对于原来size的变化比例(共有两个比例值,scale_width,scale_height),然后将size信息和location信息分别乘以scale_width,scale_height后重新赋值给控件即可。
具体实现代码如下所示:
1、先实习了基本的Form页面设计(通过界面设计器拖拽控件位置即可)
2、然后实现以下类(可以自动调整Form中控件大小的类)
代码参考自:https://www.jerrycoding.com/article/winform_scale/
public partial class AutoSizeForm : Form
{
private float X, Y;
public void setTag(Control cons)//Control类,定义控件的基类
{
foreach (Control con in cons.Controls)
{
//获取或设置包含有关控件的数据的对象
con.Tag = con.Width + ":" + con.Height + ":" + con.Left + ":" + con.Top + ":" + con.Font.Size;
if (con.Controls.Count > 0)
{
setTag(con); //递归算法
}
}
}
public void setControls(float newx, float newy, Control cons)
{
foreach (Control con in cons.Controls)
{
if (!(con.Tag is null))
{
string[] mytag = con.Tag.ToString().Split(new char[] {
':' });
float a = Convert.ToSingle(mytag[0]) * newx;
con.Width = (int)a;
a = Convert.ToSingle(mytag[1]) * newy;
con.Height = (int)(a);
a = Convert.ToSingle(mytag[2]) * newx;
con.Left = (int)(a);
a = Convert.ToSingle(mytag[3]) * newy;
con.Top = (int)(a);
Single currentSize = Convert.ToSingle(mytag[4]) * newy;
con.Font = new Font(con.Font.Name, currentSize, con.Font.Style, con.Font.Unit);
if (con.Controls.Count > 0)
{
setControls(newx, newy, con); //递归
}
}
}
}
public void Form_Resize(object sender, EventArgs e)
{
float newx = (this.Width) / X; //当前宽度与变化前宽度之比
float newy = this.Height / Y; //当前高度与变化前宽度之比
setControls(newx, newy, this);
}
protected override void OnLoad(EventArgs e)
{
base.OnLoad(e);
this.Resize += new EventHandler(Form_Resize);
X = this.Width;
Y = this.Height;
setTag(this);
}
}
3、修改自定义的Form类代码,让其继承AutoSizeForm 。具体参考如下所示
之所以在第一步时,继承的是Form类,是因为继承AutoSizeForm类后设计器页面无法看到可视化的界面,会报以下错误(不影响程序运行,只是无法在可视化界面调整控件的位置)。
继承AutoSizeForm类后实现的窗体软件就可以随窗口大小调整控件大小了,如博主的2个截图,可以看到两个图片分辨率有所变化,但是控件的相对关系没有发生变化。