2017-06-26 135 views
1

我有一个添加用户按钮,当用户点击它时动态添加删除按钮和用户名文本框。用户可以多次点击该按钮,并且控件将继续添加。C#winforms动态创建按钮控件

我无法动态创建删除按钮。它应该删除它本身和旁边的用户名文本框。相反,它会始终删除已添加的顶部行。此外,当您单击添加新用户后,单击删除它不会自动填充空格 - 它将新文本框和按钮移到底线。

这里是我的代码:

private void AddUserbtn_Click_1(object sender, EventArgs e) 
{ 
    TextBox[] Username = new TextBox[n]; 
    Button[] Remove = new Button[n]; 

    int UsernameX, UsernameY, RemoveX, RemoveY; 

    UsernameX = 346; 
    UsernameY = 45; 
    RemoveX = 946; 
    RemoveY = 45; 

    for (int i = 0; i < n; i++) 
    { 
     Username[i] = new TextBox(); 
     Username[i].Size = new Size(233, 26); 
     Username[i].Location = new Point(UsernameX, UsernameY + space); 
     Username[i].Font = new Font("Arial", 10); 
     Username[i].Name = "Username" ; 

     Remove[i] = new Button(); 
     Remove[i].Location = new Point(RemoveX, RemoveY + space); 
     Remove[i].Text = "Remove"; 
     Remove[i].Font = new Font("Arial", 10); 
     Remove[i].Size = new Size(95, 23); 
     Remove[i].UseVisualStyleBackColor = true; 
     Remove[i].Click += new EventHandler(Remove_Click); 
     Remove[i].Name = "Remove"; 

     space += 35; 
    } 

    for (int i = 0; i < n; i++) 
    { 
     CaeUsersPanel.Controls.Add(Username[i]); 
     CaeUsersPanel.Controls.Add(Remove[i]); 
    } 
} 

private void Remove_Click(object sender, EventArgs e) 
{ 
    CaeUsersPanel.Controls.Remove(CaeUsersPanel.Controls[("Username")]); 
    CaeUsersPanel.Controls.Remove(CaeUsersPanel.Controls[("Remove")]); 
} 
+0

嗨@Julie我有一个问题,当你点击添加按钮它应该删除自己? – Esperadoce

+0

添加用户按钮将始终在那里。当你点击添加它会创建一个新的文本框和按钮,当你点击新的按钮时,它应该删除它自己和新的文本框。但添加按钮将始终存在 – Julie

+0

所有这些控件都具有相同的名称。所以按名称删除不起作用。您可以从* sender *参数获得对该按钮的引用。考虑使用Tag属性来存储对文本框的引用。 Controls.Remove()不够好,你*必须*使用Dispose()来真正摆脱控制。 –

回答

-1

卸下两个最后创建:

private void Remove_Click(object sender, EventArgs e) 
{ 
    this.Controls.Remove(this.Controls[this.Controls.Count - 1]); 
    this.Controls.Remove(this.Controls[this.Controls.Count - 1]); 
} 
+0

删除了页面上的所有控件 – Julie

0

把一类变种存储Button - TextBox对,分别删除。快速测试下面的代码 - 没有针对内存泄漏/逻辑等进行微调,只是满足您的要求的示例代码。

Dictionary<Button, TextBox> pair = new Dictionary<Button, TextBox>(); // A dictionary to store the Button - TextBox pair 

private void button1_Click(object sender, EventArgs e) { 
    int n = 3; // Added for testing 
    int space = 0; // Added for testing 

    int UsernameX, UsernameY, RemoveX, RemoveY; 

    UsernameX = 100; // Modified for testing 
    UsernameY = 45; 
    RemoveX = 400; // Modified for testing 
    RemoveY = 45; 

    for (int i = 0; i < n; i++) { 
     var Username = new TextBox(); 
     Username.Size = new Size(233, 26); 
     Username.Location = new Point(UsernameX, UsernameY + space); 
     Username.Font = new Font("Arial", 10); 
     Username.Name = "Username"; 

     var Remove = new Button(); 
     Remove.Location = new Point(RemoveX, RemoveY + space); 
     Remove.Text = "Remove"; 
     Remove.Font = new Font("Arial", 10); 
     Remove.Size = new Size(95, 23); 
     Remove.UseVisualStyleBackColor = true; 
     Remove.Click += new EventHandler(Remove_Click); 
     Remove.Name = "Remove"; 

     Controls.Add(Username); 
     Controls.Add(Remove); 

     pair.Add(Remove, Username); 

     space += 35; 
    } 
} 
private void Remove_Click(object sender, EventArgs e) { 
    Controls.Remove((Button)sender); // Removes the delete button 
    Controls.Remove(pair[(Button)sender]); // Removes the textbox 
    pair.Remove((Button)sender); // Removes the entry in dictionary 
} 

更新:更好的内存和逻辑问题的另一个版本。如果是OP的愿望,还可以将其余的控制权提升。

int n = 3; // Added for testing, probably you already have it somewhere 
int space = 0; // Added for testing, probably you already have it somewhere 

// Moved for logic 
// Value modified for testing 
int UsernameX = 100; 
int UsernameY = 45; 
int RemoveX = 400; 
int RemoveY = 45; 

int SpaceDelta = 35; // Added for logic 

List<Button> RemoveButtons = new List<Button>(); 
List<TextBox> UsernameTextBoxes = new List<TextBox>(); 

private void button1_Click(object sender, EventArgs e) { 

    Random rnd = new Random((int)DateTime.Now.Ticks); // Added for testing 

    for (int i = 0; i < n; i++) { 
     var Username = new TextBox(); 
     Username.Size = new Size(233, 26); 
     Username.Location = new Point(UsernameX, UsernameY + space); 
     Username.Font = new Font("Arial", 10); 
     Username.Name = "Username"; 
     Username.Text = $"{(int)(rnd.NextDouble() * 100000)}"; // Added for testing 

     var Remove = new Button(); 
     Remove.Location = new Point(RemoveX, RemoveY + space); 
     Remove.Text = $"{(int)(rnd.NextDouble() * 100000)}"; // Modified for testing 
     Remove.Font = new Font("Arial", 10); 
     Remove.Size = new Size(95, 23); 
     Remove.UseVisualStyleBackColor = true; 
     Remove.Click += new EventHandler(Remove_Click); 
     Remove.Name = "Remove"; 

     Controls.Add(Username); 
     Controls.Add(Remove); 

     RemoveButtons.Add(Remove); 
     UsernameTextBoxes.Add(Username); 

     space += SpaceDelta; 
    } 
} 
private void Remove_Click(object sender, EventArgs e) { 
    int idx = RemoveButtons.IndexOf((Button)sender); 

    // Remove button 
    RemoveButtons[idx].Dispose(); 
    RemoveButtons.RemoveAt(idx); 

    // Remove textbox 
    UsernameTextBoxes[idx].Dispose(); 
    UsernameTextBoxes.RemoveAt(idx); 

    // Shift controls up 
    for (int i = idx; i < RemoveButtons.Count; i ++) { 
     RemoveButtons[i].Top -= SpaceDelta; 
     UsernameTextBoxes[i].Top -= SpaceDelta; 
    } 

    space -= SpaceDelta; 
} 
+0

删除控件不会处理它。如果您处理该控件,它将自动从控件集合中删除。 – LarsTech

+0

@LarsTech正如我所说的,我没有打扰内存泄漏,只关注功能。 PS,将'pair.Remove((Button)sender)'配置控件? –

+0

不,它不会。您必须在控件上调用Dispose。我忽略了您的免责声明,因为您的答案从长远来看并不能帮助用户。使用此代码的 – LarsTech