0

有一个带有 2 个面板、一个数据网格视图和一个“清除”按钮的标签页。面板中只有文本框,并且网格是未绑定的。数据由用户输入。默认情况下,清除 btn 是禁用的。我的要求是当任何文本框不为空或网格中有超过 1 行时才启用它。此代码不起作用。请帮忙。

public Form1()
 {
   InitializeComponent();
   foreach (Control c in InvoiceTab.Controls)
    {
      if (c is DataGridView)
       {
         DataGridView dgv = c as DataGridView;
         if (dgv.RowCount > 1)
          {
            EnableClearBtnBool = true;
            btnClear.Enabled = true;
            break;
          }
         else
          {
            EnableClearBtnBool = false;
            btnClear.Enabled = false;
            break;
          }
       }
    }
    foreach (Control c1 in panel1.Controls)
     {
       if (c1 is TextBox)
        {
          if (c1.Text != "")
            {
              EnableClearBtnBool = true;
              c1.TextChanged -= EnableClearBtn;
              c1.TextChanged += EnableClearBtn;
              break;
            }
          else
             EnableClearBtnBool = false;
        }                  
     }
     foreach (Control c2 in panel2.Controls)
      {
        if (c2 is TextBox)
         {
           if (c2.Text != "")
            {
              EnableClearBtnBool = true;
              c2.TextChanged -= EnableClearBtn;
              c2.TextChanged += EnableClearBtn;
              break;
            }
           else
            EnableClearBtnBool = false;
         }
      }      
 }
bool EnableClearBtnBool = false;
private void EnableClearBtn(object sender, EventArgs e)
    {
        if (EnableClearBtnBool == true)
            btnClear.Enabled = true;
        else
            btnClear.Enabled = false;
    }
4

1 回答 1

1

该代码几乎可以肯定是因为它的位置首先不起作用。但是,我们也应该能够做出一些根本性的改变。首先,我们需要在一个可以经常调用的方法中使用此代码:

private void RefreshClearButton()
{
    btnClear.Enabled = textBox1.Text.Length > 0 ||
        textBox2.Text.Length > 0 || ...
        dataGridView.RowCount > 1;
}

但是,我们还需要利用所有文本框TextChanged上的事件:

private void textBox_TextChanged(object sender, EventArgs e)
{
    RefreshClearButton();
}

所以你需要将它们全部连接到这个事件处理程序。现在,我们还有两个需要消耗的事件,在DataGridViewRowsAddedRowsRemoved

private void dataGridView_RowsAdded(object sender, DataGridViewRowsAddedEventArgs e)
{
    RefreshClearButton();
}

private void dataGridView_RowsRemoved(object sender, DataGridViewRowsRemovedEventArgs e)
{
    RefreshClearButton();
}

所以现在每次发生变化时我们都会收到通知。如果您必须遍历面板而不是沿途命名每个文本框,那么您可能需要执行以下操作:

private bool HasTextBeenEntered(ControlCollection controls)
{
    foreach (var c in controls)
    {
        if (c is TextBox && ((TextBox)c).Text.Length > 0) { return true; }
        else if (c is Control && HasTextBeenEntered(((Control)c).Controls)) { return true; }
    }

    return false;
}

RefreshClearButton这会稍微改变方法:

private void RefreshClearButton()
{
    btnClear.Enabled = HasTextBeenEntered(this.Controls) || dataGridView.RowCount > 1;
}

免责声明:此代码均未编译,因此如果您必须对其进行调整,请不要感到惊讶,但它会让您完成 90% 以上的工作。

于 2013-04-23T18:41:09.907 回答