I struggled with very same issue about a year ago. Everything I found on the web was pretty nasty (i.e. iterate over controls and catch every control focus thus firing validate event or some solution that heavily relied on pinvoke or reflection - I don't exactly remember).
I ended up creating wrappers that included Validate method for my textboxes etc. and keeping collection of this wrappers. This way, I could iterate over my wrappers and call validate for every control.
That solution worked fine. First I tried the solution with programmatically catching every control focus but I had lots of problems with it. After wasting some time trying to improve this solution I decided to create these wrappers and this was very good decision.
UPDATE
Here how it looked like. Inform I declare list of controls that need to be validated:
private List<TextBoxWithValidation> textBoxesWithValidation;
In constructor I add controls to the list:
TextBoxWithValidation emailTextBoxWithValidation = new TextBoxWithValidation(emailTextBox);
emailTextBoxWithValidation.AddValidationPair(Validator.ValidationType.VALIDATE_NOT_EMPTY, "ValidateNotEmptyEmail");
emailTextBoxWithValidation.AddValidationPair(Validator.ValidationType.VALIDATE_EMAIL, "ValidateEmailEmail");
textBoxesWithValidation.Add(emailTextBoxWithValidation);
Then I am able to validate the form:
private bool ValidateForm()
{
foreach (TextBoxWithValidation textBoxWithValidation in textBoxesWithValidation)
{
if (!textBoxWithValidation.Validate())
{
return false;
}
}
return true;
}
And textbox with validation looks like this:
class TextBoxWithValidation
{
class ValidationTypeMessagePair
{
public Validator.ValidationType ValidationType { get; set; }
public string ValidationMessage { get; set; }
public ValidationTypeMessagePair(Validator.ValidationType validationType, string validationMessage)
{
this.ValidationType = validationType;
this.ValidationMessage = validationMessage;
}
}
private List<ValidationTypeMessagePair> validationPairs;
private TextBox textBox;
public TextBoxWithValidation(TextBox textBox)
{
this.textBox = textBox;
this.textBox.DataBindings["Text"].DataSourceUpdateMode = DataSourceUpdateMode.Never;
validationPairs = new List<ValidationTypeMessagePair>();
}
public void AddValidationPair(Validator.ValidationType validationType, string validationMessage)
{
validationPairs.Add(new ValidationTypeMessagePair(validationType, validationMessage));
}
public bool Validate()
{
foreach (ValidationTypeMessagePair validationPair in validationPairs)
{
if (!Validator.Validate(validationPair.ValidationType, textBox, Messages.Localize(validationPair.ValidationMessage))) return false;
}
textBox.DataBindings["Text"].WriteValue();
return true;
}
public void ClearValidationStatus()
{
textBox.BackColor = System.Drawing.SystemColors.Window;
}
}