如何使用代码隐藏自定义控件?

时间:2015-12-30 18:05:14

标签: forms winforms

在这里,我从自定义控件创建两个对象并将它们添加到表单中,但它只显示第一个,为什么?

 private void frmWelcome_Load(object sender, EventArgs e)

    {
        // Count number of Contacts in XML
        XmlDocument doc = new XmlDocument();
        doc.Load(@"C:\Users\Taha\Documents\Visual Studio 2013\Projects\ContactsMangementSystem\ContactsMangementSystem\ContactsData.xml");
        int numOfContacts = doc.GetElementsByTagName("Contact").Count;

        XmlNodeList nodelist = doc.GetElementsByTagName("Contact");
        foreach (XmlNode item in nodelist)
        {
            // Create Control for each Item
            ContactControl.ContactControl userControl = new ContactControl.ContactControl();
            // Fill Control With Data
            userControl.labelOrganizationText = item.ChildNodes.Item(5).InnerText;
            userControl.labelTitleText = item.ChildNodes.Item(0).InnerText;
            userControl.labelWorkAddressText = item.ChildNodes.Item(12).InnerText;
            userControl.labelWorkPhoneText = item.ChildNodes.Item(8).InnerText;
            userControl.labelEmailText = item.ChildNodes.Item(7).InnerText;
            Image img = Image.FromFile(item.ChildNodes.Item(9).InnerText);
            userControl.ContactImage = img;
            // Add item to the form
            this.Controls.Add(userControl);

        }
        ContactControl.ContactControl  userControl2 = new ContactControl.ContactControl();
        this.Controls.Add(userControl2);
    }

1 个答案:

答案 0 :(得分:0)

如果您将所有控件(也称为programmaticaly)添加到表单的Control集合中,您将负责处理位置,边界,大小等。我将使用修剪后的代码演示您的问题的根本原因与你的相似的例子。

首先,我创建一个UserControl,其上有一个标签。将标签属性Dock设置为Fill,将Font设置为Point 28,将TextAlign设置为MiddelCentre,将最重要的修改器设置为Public:

usercontrol with label

现在我们在Designer中创建一个新表单,并为其添加一个Timer,一个Button,两个复选框和一个FlowLayoutPanel。 FlowLayoutPanel将其Anchor属性设置为Top,Left,Right,Bottom,因此如果表单调整大小,它将调整大小。我们的设计如下:

form with button, checkboxes and flowlayoutpanel

Timer_Tick event中创建了UserControl的新实例,并将其添加到Forms Control collection或FlowLayoutPanel。有两个变量可以跟踪创建的控件数量以及控件需要的位置。

以下是表单代码隐藏中的代码:

int position = 0; // what position the control should be
int controlsCreated = 0; // how many controls did we create

private void timer1_Tick(object sender, EventArgs e)
{
    // create the control
    var ucnext = new UserControl1();
    controlsCreated++;
    ucnext.label1.Text = controlsCreated.ToString();

    // where are we adding the control?
    if (!chkFlow.Checked)
    {
        // do we want to use the Location?
        // if not Top will be 0
        if (chkLocation.Checked)
        {
            // Ok, position times height should gives us
            // a free spot
            ucnext.Top = position * ucnext.Height;
            position++;
        }
        this.Controls.Add(ucnext);
        ucnext.BringToFront(); // otherwise we always see control 1
    } else
    {
        // now the FlowLayout takes over all Layout logic
        this.flowLayoutPanel1.Controls.Add(ucnext);
    }
}

private void button1_Click(object sender, EventArgs e)
{
    this.timer1.Enabled = !this.timer1.Enabled;
    this.btnStart.Text = this.timer1.Enabled ? "Pause" : "Continue";
}

如果我们运行此操作,我们可以选中并取消选中Location和添加到flowlayout的选项,以查看直接向表单或FlowLayout面板添加控件的各种效果。

loop with adding controls

因此,请记住,如果您自己向Form的Control集合添加控件,请确保将其Location属性(Top,Left)设置为合适的值。如果你做错了,你的控件最终会隐藏在另一个控件后面,或者放在窗体的可见边界之外。如果你事先不知道有多少控件你会考虑使用其中一个容器控件,比如FlowLayoutPanel。