4

i am working on an software in which i want to clear each thing after doing achieving a specific task, like clearing all the fields, list view etc etc and i've to write the a lot of things to be cleared off, like the code of my new button is:

 private void btnNew_Click(object sender, EventArgs e)
    {
        txtProductCode1.ReadOnly = false;
        txtInvoiceNo.ReadOnly = false;
        cmbCustoemerType.Enabled = false;
        cmbCustomerName.Enabled = false;
        button1.Enabled = true;
        txtProductCode1.Text = null;
        txtWageName.Text = null;
        txtWageCost.Text = null;
        btnFirst.Visible = false;
        btnPrevious.Visible = false;
        btnNext.Visible = false;
        btnLast.Visible = false;
        cmbProductName.Enabled = true;
        txtQty.ReadOnly = false;
        txtPercant.ReadOnly = false;
        txtDiscount.ReadOnly = false;
        cmbCustoemerType.Enabled = true;
        cmbCustomerName.Enabled = true;
        button5.Enabled = true;
        btnDelete.Enabled = true;
        dtp1.Enabled = true;
        btnSave.Text = "&Save";

        cmbCustoemerType.Text = null;
        cmbCustomerName.Text = null;
        txtInvoiceNo.Clear();
        txtDiscount.Clear();
        txtGrandTotal.Clear();
        txtProductName.Clear();
        txtSalePrice.Clear();
        txtQty.Clear();
        txtTotal.Clear();

        txtExtraWages.Text = null;
        lvExtraWages.Items.Clear();
        lvTransaction.Items.Clear();
        lblCount.Text = null;
        lblNetTotal.Text = null;
        txtPercant.Text = null;

        txtInvoiceNo.Text = invoice.ToString();
    }

is there any way to get rid of writing the code again n again, like i need to enable one thing which i've disabled here on another button so i have to write reverse code of this to achieve the task and it's really annoying! is there any other way to do this?

EDIT:

tried following code:

private void btnNew_Click(object sender, EventArgs e)
        {   
           //using setboxdefault function
            SetTextBoxDefaults();

            cmbCustoemerType.Text = null;
            cmbCustomerName.Text = null;
        cmbCustoemerType.Enabled = false;
        cmbCustomerName.Enabled = false;
        cmbProductName.Enabled = true;
        cmbCustoemerType.Enabled = true;
        cmbCustomerName.Enabled = true;

        button5.Enabled = true;
        btnDelete.Enabled = true;  
        button1.Enabled = true;          
        btnFirst.Visible = false;
        btnPrevious.Visible = false;
        btnNext.Visible = false;
        btnLast.Visible = false;          


        btnSave.Text = "&Save";

        lvExtraWages.Items.Clear();
        lvTransaction.Items.Clear();

        lblCount.Text = null;
        lblNetTotal.Text = null;

        dtp1.Enabled = true;

        txtInvoiceNo.Text = invoice.ToString();
    }

    private void SetTextBoxDefaults()
    {
        var textBoxes = GetControls(this, typeof(TextBox));
        foreach (var textBox in textBoxes)
        {
            TextBox.Clear();
        }
    }

    public IEnumerable<Control> GetControls(Control control, Type type)
    {
        var controls = control.Controls.Cast<Control>();
        return controls.SelectMany(ctrl => GetControls(ctrl, type)).Concat(controls).Where(c => c.GetType() == type);
    }

but it's giving error on TextBox.Clear(); , error is Error 4

An object reference is required for the non-static field, method, or property 'System.Windows.Forms.TextBoxBase.Clear()'    

Please let me know where i am mistaking..!!

braX
  • 11,506
  • 5
  • 20
  • 33
Jack Frost
  • 277
  • 2
  • 3
  • 12

3 Answers3

3

Remember to stay DRY

Partition the reset logic into suitable, small methods that reset a logical grouping of controls. Then invoke those methods where and as needed.

Nicholas Carey
  • 71,308
  • 16
  • 93
  • 135
3

As Tim has suggested, you can iterate though the controls and set each one accordingly..

public IEnumerable<Control> GetControls(Control control,Type type)
{
    var controls = control.Controls.Cast<Control>();
    return controls.SelectMany(ctrl => GetControls(ctrl,type)).Concat(controls).Where(c => c.GetType() == type);
}

private void btnNew_Click(object sender, EventArgs e)
{
    SetComboBoxDefaults();
    SetTextBoxDefaults();
    SetButtonDefaults();
}

private void SetComboBoxDefaults()
{
    var comboBoxes = GetControls(this, typeof(ComboBox));
    foreach (var comboBox in comboBoxes)
    {
        ((ComboBox)comboBox).Enabled = false;
        ((ComboBox)comboBox).Text = null;
    }
}

private void SetTextBoxDefaults()
{
    var textBoxes = GetControls(this, typeof(TextBox));
    foreach (var textBox in textBoxes)
    {
        ((TextBox)textBox).Clear();
    }
}

private void SetButtonDefaults()
{
    var buttons = GetControls(this, typeof(Button));
    foreach (var button in buttons)
    {
        ((Button)button).Visible = false;

        if (button.Name == "btnSave") ((Button)button).Text = "&Save";
    }
}

You can also have separate GetControl methods so that it returns a specific type of Control, reducing the need to cast to derived types.

update for edit:

You are using the TextBox type instead of the variable name in the foreach loop. Update it to use textBox (lowercase), not TextBox (pascal) see below:

private void SetTextBoxDefaults()
{
    var textBoxes = GetControls(this, typeof(TextBox));
    foreach (var textBox in textBoxes)
    {
        ((TextBox)textBox).Clear();
    }
}
d.moncada
  • 16,900
  • 5
  • 53
  • 82
  • woww, finally some nice and clean code... i am surely gonna try this – Jack Frost Feb 12 '14 at 20:38
  • 1
    @JackFrost you may need to add some specific conditioning based on control name, if it differs from all other controls of the same type (as shown in SetButtonDefaults()) – d.moncada Feb 12 '14 at 20:39
  • now this error is coming Error 1 'System.Windows.Forms.Control' does not contain a definition for 'Clear' and no extension method 'Clear' accepting a first argument of type 'System.Windows.Forms.Control' could be found (are you missing a using directive or an assembly reference?) – Jack Frost Feb 13 '14 at 17:07
  • it's cool working now, but if i've to null some textboxes but not the all?? @d.moncada – Jack Frost Feb 13 '14 at 21:21
2

What I have done in several such cases is this:

void SetTextBoxReadOnly(bool val, param TextBox[] textBoxes)
{
    if(textBoxes != null && textBoxes.Length > 0)
    {
        foreach(TextBox textBox in textBoxes)
        {
            if(textBox != null)
            {
                textBox.ReadOnly = val;
            }
        }
    }
}

void SetControlEnabled(bool val, param Control[] ctrls)
{
    if(ctrls != null && ctrls.Length > 0)
    {
        foreach(Control ctrl in ctrls)
        {
            if(ctrl != null)
            {
                ctrl.Enabled = val;
            }
        }
    }
}

// etc set of methods for similar situations.
// there methods can be invoked as

...
...
...

SetTextBoxReadOnly(true, txtProductCode1,
                         txtInvoiceNo,
                         txtQty,
                         txtPercant,
                         txtDiscount);
Abhinav
  • 2,085
  • 1
  • 18
  • 31
  • 1
    @AhsanMughal - There might be some negative side-effect of this approach, but I am yet to see anything. Moreover it helps me keep the code clean and relevant. – Abhinav Feb 12 '14 at 20:30