Search code examples
c#winformsuser-interfacetoolstripbutton

Handle NumericUpDown.ValueChanged event before ToolStripButton.Click event


I have a form with the NumericUpDown and the ToolStripButton.

In the NumericUpDowns ValueChanged event handler the value of some object instance is changed.

In the ToolStripButtons Click event handler the object instance is saved.

Now the problem is that if I rewrite the value in the NumericUpDown and then click on the ToolStripButton to save the state the ToolStripButtons Click event is fired before the NumericUpDowns ValueChanged event so I first save the instance and after that I changed it.

public partial class Form2 : Form
{
    private Foo _foo = new Foo();

    public Form2()
    {
        InitializeComponent();
    }

    private void NumericUpDown1_ValueChanged(object sender, EventArgs e)
    {
        _foo.Value = numericUpDown1.Value;
    }

    private void ToolStripButton1_Click(object sender, EventArgs e)
    {
        _foo.Save();
    }

    private class Foo
    {
        public decimal Value { get; set; }

        public void Save()
        {
            //Save the value...
        }
    }
}

What is the best way to solve this?
Those events are fired in the correct order if I use the Button control, but not if I use the ToolStripButton control.


Solution

  • As an option, instead of ValueChanged, handle Validated event of NumericUpDown and also in the Click event handler of ToolStripButton, call this.Validate() before save:

    private void NumericUpDown1_Validated(object sender, EventArgs e)
    {
        _foo.Value = numericUpDown1.Value;
    }
    
    private void ToolStripButton1_Click(object sender, EventArgs e)
    {
        this.Validate();
        _foo.Save();
    }
    

    Note: If there are other controls on the form which may have Validating event and you may set e.Cancel = true for them, you need to check the result of Validate method before calling Save, using if(this.Validate()){ /*...*/ }.