当使用this.validateChildren()时,我如何为所有无效的表单控件设置一个errorProvider?

4

如果我漏看了一些显而易见的东西,请谅解。

问题背景

我有一个应用程序,允许用户填写表单,表单内容将上传到数据库。当他们点击“上传”按钮时,必须验证表单。如果任何字段无效,系统会向用户发出警报。

当前解决方案

当用户点击上传交易按钮时,将调用validFormSelections()函数。

if (!this.validateChildren())
{
    // Display an error
    return false;
}
else
{
    return true; 
}

对于每个下拉框,都会调用验证方法,例如:
cmbName_Validating(object sender, CancelEventArgs e)
{
    if (/* not valid for whatever reason */)
    {
        errorProvider.Clear();
        e.Cancel = true; 
        errorProvider.setError((Control)sender, /* suitable error message */)
    }
    else
    {
        errorProvider.SetError((Control)sender, ""); 
    }
} 

问题

我想要做的是,在所有不合法的字段旁边显示errorProvider,但是目前由于在单个验证方法中设置了e.Cancel = true;,那么(如果我的理解是正确的)一旦找到第一个无效字段,它就不会继续验证其他字段。

我如何才能调用this.validateChildren()并仍然在所有无效字段旁边显示errorProvider

到目前为止研究解决方案的尝试

  • 据我所知,我的问题在于需要将CancelEventArgsCancel属性设置为真,因为它“截断”了其余的验证。因此,找到一种避免在稍后或找到一种绕过此问题的方法似乎是一个好主意。但我不确定该如何去做。

  • 我的其中一个最初的想法是,如果只能从每个验证事件处理程序返回boolean,那么我可以相当容易地解决这个问题(但我怀疑,并且已经学到,我不能这样做)。我在事件处理程序中看到了一种替代返回值的方法是传递一个可变值(例如CancelEventArgs本身)。这似乎可能是一个合适的解决方案,但我不确定如何自己做到这一点...

1个回答

3

问题当然是设置 e.Cancel = true。所以不要这样做。通常情况下,这是一个非常不愉快的功能,使得数据输入变得非常模态。更友好的方法是让用户自由地完成数据输入任务,按照您设置的选项顺序输入数据并不一定是最佳的。

只需编写一个小的辅助方法即可轻松实现。例如:

    private Control firstInvalidControl;

    private void SetValidation(object sender, bool ok, string errMsg) {
        var ctl = (Control)sender;
        if (ok) errorProvider1.SetError(ctl, "");
        else {
            if (firstInvalidControl == null) firstInvalidControl = ctl;
            errorProvider1.SetError(ctl, errMsg);
        }
    }

在控件的Validating事件处理程序中调用SetValidation()。现在,您可以轻松地获得所有适当的警告显示,并帮助用户导航到他可能需要首先处理的控件。例如:
    private void OKButton_Click(object sender, EventArgs e) {
        firstInvalidControl = null;
        this.ValidateChildren();
        if (firstInvalidControl != null) firstInvalidControl.Focus();
        else {
            // Data is good, use it
            // ...                
        }
    }

非常感谢您的帮助!很抱歉花了这么长时间才接受它作为答案 - 我忙于其他项目,没有时间尝试实现它。一个优秀而优雅的解决方案! - Eilidh

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接