【发布时间】:2016-07-23 00:50:28
【问题描述】:
我正在尝试制作一个 winForms 应用程序,其中,numericUpDown 的每次增加最终都应该使面板控件可见,并创建一个文本框控件、一个图片框、一个 numericUpDown 控件和三个标签。而且每次减少,都应该去掉这组控件。我已经设法编写了创建控件的代码,但我不知道如何删除它们。我唯一的猜测是为每个控件分配一个名称,然后使用colorPanel.Controls.RemoveByKey()。不太确定如何处理nameTextBoxPositionY 和newLabelPositionY,在他们目前的状态下,他们可能会搞砸一切。还是我应该放弃,使用switch(regionNumber),手动创建控件,然后根据 numericUpDown 值使它们可见?考虑到 numericUpDown 的最大值是 10,这将是一件很麻烦的事。
private Label newLabel;
private TextBox nameTextBox;
private NumericUpDown heightNumericUpDown;
private PictureBox colorPictureBox;
private string[] newLabelText = {"Name", "Height", "Color"};
private int newLabelPositionX = -3;
private int newLabelPositionY = 5;
private int nameTextBoxPositionX = 74;
private int nameTextBoxPositionY = 2;
private void numberOfRegions_ValueChanged(object sender, EventArgs e)
{
int regionNumber = Convert.ToInt32(numberOfRegions.Value);
int numberOfLabels = 3;
if (regionNumber > 0)
{
colorPanel.Visible = true;
for (int i = 0; i < regionNumber; i++)
{
nameTextBox = new TextBox();
nameTextBox.Size = new System.Drawing.Size(81, 20);
nameTextBox.Location = new System.Drawing.Point(nameTextBoxPositionX, nameTextBoxPositionY);
colorPanel.Controls.Add(nameTextBox);
nameTextBoxPositionY += 78;
for (int a = 0; a < numberOfLabels; a++)
{
newLabel = new Label();
newLabel.Location = new System.Drawing.Point(newLabelPositionX, newLabelPositionY);
newLabel.Text = newLabelText[a];
colorPanel.Controls.Add(newLabel);
newLabelPositionY += 26;
}
}
newLabelPositionY = 5;
nameTextBoxPositionY = 2;
}
else
{
colorPanel.Visible = false;
}
}
【问题讨论】:
-
这里的所有答案都有一个非常、非常严重的错误。从其父控件集合中移除的控件必须被释放。不这样做会导致垃圾收集器无法修复的永久内存泄漏。顺便说一句,使用任务管理器轻松诊断,添加 USER Objects 列。您会看到您的流程显示的数字不断增加。您的程序在达到 10,000 时崩溃。
-
那么应该如何处理这些控件呢?我想,这并不像在
for循环中调用nameTextBox.Dispose()那样简单。 -
只需编写一个存储对这 4 个控件的引用的小结构。使用
Stack<>来存储它们。现在很简单。 -
你需要使用用户控件