c#如何创建按钮并稍后通过ID

时间:2016-06-21 18:28:29

标签: c# winforms flowlayoutpanel

我很难创建这个脚本来生成好友请求。我需要为每个按钮和标签专门添加一个id,以便在用户点击“接受”或“拒绝”按钮时将其删除。

Button reqAccept;
Button reqReject;
Label reqUserName;

private void loadFriendRequests()
{
    using (SqlConnection connection = new SqlConnection(con))
    {
        using (SqlCommand cmd = new SqlCommand("Select UserFirstName, UserLastName, FriendEmail From PendingRequests Where FriendEmail = @fe", connection))
        {
            connection.Open();
            cmd.Parameters.AddWithValue("@fe", Properties.Settings.Default.Email);
            using (SqlDataReader dr = cmd.ExecuteReader())
            {
                i = 0;
                while (dr.Read())
                {
                    i++;
                    foreach (object request in i.ToString())
                    {
                        Label userName = new Label();
                        Button accept = new Button();
                        Button reject = new Button();

                        accept.Click += Accept_Click;
                        reject.Click += Reject_Click;

                        userName.Text = CultureInfo.CurrentCulture.TextInfo.ToTitleCase(dr["UserFirstName"].ToString() + " " + dr["UserLastName"].ToString());

                        accept.Text = "Accept";
                        reject.Text = "Reject";

                        friendRequestPanel.Controls.Add(userName);
                        friendRequestPanel.Controls.Add(accept);
                        friendRequestPanel.Controls.Add(reject);

                        reqAccept = accept;
                        reqReject = reject;
                        reqUserName = userName;
                    }
                }
            }
        }
    }
    Requests.Start();
}
private void Reject_Click(object sender, EventArgs e)
{
    friendRequestPanel.Controls.Remove(reqUserName);
    friendRequestPanel.Controls.Remove(reqAccept);
    friendRequestPanel.Controls.Remove(reqReject);

    updateFriendRequestDatabase(2);
}
private void Accept_Click(object sender, EventArgs e)
{
    friendRequestPanel.Controls.Remove(reqUserName);
    friendRequestPanel.Controls.Remove(reqAccept);
    friendRequestPanel.Controls.Remove(reqReject);

    updateFriendRequestDatabase(1);
}

代码正在做什么: 上面的代码是选择与用户的电子邮件相同的请求,并且对于每个朋友请求,它将使用标签和2个按钮将其添加到“FlowLayourPanel”以接受或拒绝。

这就是GUI的样子:GUI

当用户点击按钮时,它显然会转到事件处理程序但是如何识别按下了哪个按钮?

它必须是:

friendRequestPanel.Controls.Remove(reqUserName##ID##);

2 个答案:

答案 0 :(得分:4)

要做的第一件事是从查询中检索唯一标识数据的值。假设您的PendingRequest表具有IDRequest,那么您的查询可以更改为

  using (SqlCommand cmd = new SqlCommand(@"Select IDRequest, UserFirstName, 
                      UserLastName, FriendEmail 
                      From PendingRequests 
                      Where FriendEmail = @fe", connection))

现在,当您动态创建控件时,您还要将该ID添加到该记录创建的每个控件的Tag属性中

foreach (object request in i.ToString())
{
    Label userName = new Label();
    Button accept = new Button();
    Button reject = new Button();

    int idRequest = Convert.ToInt32(dr["IDRequest"]);
    userName.Tag = idRequest;
    accept.Tag = idRequest;
    reject.Tag = idRequest;
    ....

最后,在您的点击事件中,您可以使用类似

的代码检索按钮和标签的确切实例
private void Reject_Click(object sender, EventArgs e)
{
    Button c = sender as Button;
    int idRequest = Convert.ToInt32(c.Tag);
    var ctrls = friendRequestPanel.Controls
                                  .Cast<Control>()
                                  .Where(x => x.Tag != null &&
                                         Convert.ToInt32(x.Tag) == idRequest)
                                  .ToList();
    foreach(Control ct in ctrls)
    {
          friendRequestPanel.Controls.Remove(ct);
          ct.Dispose();
    }
    updateFriendRequestDatabase(2);
}

请注意,如果从Controls集合中删除控件,则不应忘记Dispose it。

答案 1 :(得分:1)

@Steve已经很好地回答了这个问题。他已经向您展示了如何修复当前的代码。

我想建议您构建当前代码的更好方法,以便它看起来更干净,并且您可以更好地控制好友请求功能。如果您有兴趣,请进一步阅读。如果您处于紧迫的期限内,请忽略:)。

如果我在你的位置,我会创建一个用户控件来表示个别朋友的请求,并使用事件在接受/拒绝的情况下通知主表单,以便它可以从面板/列表中删除请求。这样,主表单代码(设计者+代码隐藏)将变得更清晰,以便阅读和理解。

<强> FriendRequestControl

这是标准的UserControl,其中包含1 Label(用于显示朋友的姓名和2 Buttons接受和拒绝。

public partial class FriendRequestControl : UserControl
{
    public event EventHandler Accepted;
    public event EventHandler Rejected;

    public FriendRequestControl()
    {
        InitializeComponent();
    }

    public int RequestId { get; set; }
    public string FriendName { set { lblFriend.Text = value; } } // TODO add empty/null checks on value

    private void Accept_Click(object sender, EventArgs e)
    {
        UpdateRequest(1);
        OnAccepted();
    }

    private void Reject_Click(object sender, EventArgs e)
    {
        UpdateRequest(2);
        OnRejected();
    }

    private bool UpdateRequest(int flag)
    {
        // Update db using RequestId and flag
        // TODO Return True/False based if update succeeds
        return true; 
    }

    private void OnAccepted()
    {
        var acceptedHandler = Accepted;
        if (acceptedHandler != null)
        {
            acceptedHandler(this, EventArgs.Empty);
        }
    }

    private void OnRejected()
    {
        var rejectedHandler = Rejected;
        if (rejectedHandler != null)
        {
            rejectedHandler(this, EventArgs.Empty);
        }
    }
}

主要表格

private void Form1_Load(object sender, EventArgs e)
{
    // Showing just 1 request here
    var friendRequest = new FriendRequestControl
    {
        RequestId = 100, // As Steve mentioned, you db must return this.
        FriendName = "Friend 1"
    };

    friendRequest.Accepted += FriendRequest_Accepted;
    friendRequest.Rejected += FriendRequest_Rejected;

    flowLayoutPanel1.Controls.Add(friendRequest);
}

private void FriendRequest_Rejected(object sender, EventArgs e)
{
    var friendRequest = sender as FriendRequestControl;
    flowLayoutPanel1.Controls.Remove(friendRequest);
}

private void FriendRequest_Accepted(object sender, EventArgs e)
{
    var friendRequest = sender as FriendRequestControl;
    flowLayoutPanel1.Controls.Remove(friendRequest);
}