本篇博客只针对本人在尝试做一个界面放大问题中所遇到的一些问题:
目的: 实现窗口放大,窗口内的控件也等比放大;(成功)
1.anchor属性改变取得的效果不理想;
2.控件放大比例不一样;
3.在放大的过程中出现界面乱(看起来软件有点像盗版)
下面以下图为例讲解:
当我们设计好窗口后是这样的:
当我们拉大时:
网上有很多方法使用了改变anchor属性的方法;简单说一下anchor属性,就是让空间到界面上下左右的距离不变,实现效果会很奇怪,我们来看一下操作:
Anchor属性添加尝试
在控件属性中添加anchor属性:
需要哪个方向直接将方向点灰就可以:
为了取得好点的效果,我们做出以下划分:
其中红色对应:top left,淡蓝色对应:top,left,bottom,粉色对应bottom,left;
黑色对应:top,right,bottom;绿色对应right,top;紫色对应:bottom,right;
窗口拉动会感觉有脱节的样子,而且缩小还会导致控件重叠,虽然可以添加Resize 事件来改变控件的大小,但是anchor的属性特性导致操作依然很机械,我们想要控件等比例当大,间隔还要等比例放大感觉才协调的样子;如果控件少,界面简单这些操作还可以,但是假如界面复杂;这样操作估计要被老板打回来。
因为anchor的尝试让我太失望了,所以我就没有再去尝试dock去改变的,老老实实的写代码老改变大小;
代码控制放大后控件大小
双击界面窗口进入load 函数:
private void modular_calEchoPhaseFromSignal_Load(object sender, EventArgs e)
{
this.Resize += new EventHandler(modular_calEchoPhaseFromSignal1_Resize);//窗体调整大小时引发事件
X = this.Width;//获取窗体的宽度
Y = this.Height;//获取窗体的高度
setTag(this);//调用方法
}
大家自己的窗口名可能不一样不要介意,只要后面有load就可以:
添加其他函数:
private void setTag(Control cons)
{
//遍历窗体中的控件
foreach (Control con in cons.Controls)
{
con.Tag = con.Width + ":" + con.Height + ":" + con.Left + ":" + con.Top + ":" + con.Font.Size+":"+con.Name;
if (con.Controls.Count > 0)
setTag(con);
}
}
private void setControls(float newx, float newy, Control cons)
{
foreach (Control con in cons.Controls)
{
con.Visible = false;
}
//遍历窗体中的控件,重新设置控件的值
foreach (Control con in cons.Controls)
{
string[] mytag = con.Tag.ToString().Split(new char[] { ':' });//获取控件的Tag属性值,并分割后存储字符串数组
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]) * newx;//字体大小
con.Font = new Font(con.Font.Name, currentSize, con.Font.Style, con.Font.Unit);
if (con.Controls.Count > 0)
{
setControls(newx, newy, con);
}
}
foreach (Control con in cons.Controls)
{
con.Visible = true;
}
}
void modular_calEchoPhaseFromSignal1_Resize(object sender, EventArgs e)
{
float newx = (this.Width) / X; //窗体宽度缩放比例
float newy = this.Height / Y;//窗体高度缩放比例
setControls(newx, newy, this);//随窗体改变控件大小
// this.Text = this.Width.ToString() + " " + this.Height.ToString();//窗体标题栏文本
}
说明:
这些代码就是先遍历窗口控件,获得控件的高、宽、位置等属性放在字符串里,然后通过窗口改变的比例等比例放大后再赋值给控件对应的属性。(代码X,Y位置报错需要在前面的类里添加float X=0和 float Y=0哦)
- 关于resize函数的说明,上面代码中有modular_calEchoPhaseFromSignal1_Resize()函数,这不是由事件生成的,在百度上有段代码上是窗口名+_Resize()函数,其实它其实是没有添加这个事件的,也就是一个普通的函数,如果大家自己添加事件后出现窗口名+_Resize()函数,再在这个函数里添加上面的代码,在窗口运行的时候会出现错误;解决办法是删除掉resize事件。
- 在字体那块放大采用的高度放大采用的x的比列,是因为发现字体假如采用y的字体,当窗口向上拉伸的时候,字体也会放大,而且不仅是高度放大,而且长度也会变大,会让lable标签上的字被textbox盖掉。所以在字体上在放大比例采用x方向放大的比例。
- 关于con.Visible 采用的说明,这是解决窗口放大过程中发生暂时的紊乱现象,(虽然过时间很短,大概1s左右,但是能看见)经过思考,在未添加之前:各种空间重新计算位置高度等需要一定的时间,如果不改变可见性,就会窗口有点乱,所以在计算之前设置他不可见,计算之后再设置可见,那么界面上直接出现的就是已经算好的位置,界面不会出线暂时的紊乱状况。
(放大暂时出现的界面紊乱图)
下面来说另外一个大问题:就是控件放大比例不一样!看图:
正常图:缩小图:放大图依次为:
textBox后面的button与textBox高度上放大比例不一样!还是挺影响美观的, 怎么解决这个问题呢,我想到是直接用resize时间将button的高度与textBox强制相等,(原谅我没有想到聪明的方法,控件少这种方法还是可行的,只是当控件多起来的时候,这种方法就有些麻烦)加在窗口的resize事里没有用,放在textBox改变的事件里:
private void modular_genChirpSignal_Resize(object sender, EventArgs e)
{
button10.Height = textBox10.Height;
}
这样后基本完成了想要的样子,但是为了防止过度的缩小出现控件挤压问题,我就把窗口设置成不可调的模式了,改变FormBorderStyle为FixedDialog,保留最大化与最小键。后面出现了一点点小问题就是在窗口初始化后textbox与它后面的buttom又不一样大小了,于是于是在窗口初始化界面再次添加强制这两个控件高度相等的代码。
注意!: 这里的代码只是调整了界面左右控件的大小,假如界面上有图标和图片,需要将图标和图片也放大,不然调整的时候界面会出现跳、卡或者别的问题。