C# 单击表单的取消按钮后如何跳过验证

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/1882523/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-06 21:37:31  来源:igfitidea点击:

How to skip Validating after clicking on a Form's Cancel button

c#winformsvalidating

提问by user228985

I use C#. I have a Windows Form with an edit box and a Cancel button. The edit box has code in validating event. The code is executed every time the edit box loses focus. When I click on the Cancel button I just want to close the form. I don't want any validation for the edit box to be executed. How can this be accomplished?

我使用 C#。我有一个带有编辑框和取消按钮的 Windows 窗体。编辑框有验证事件的代码。每次编辑框失去焦点时都会执行代码。当我点击取消按钮时,我只想关闭表单。我不希望对编辑框执行任何验证。如何做到这一点?

Here is an important detail: if the validation fails, then

这是一个重要的细节:如果验证失败,那么

            e.Cancel = true;

prevents from leaving the control.

防止离开控件。

But when a user clicks Cancel button, then the form should be closed no matter what. how can this be implemented?

但是当用户单击取消按钮时,无论如何都应该关闭表单。如何实施?

回答by womp

Set the CausesValidationproperty of the Cancel button to false.

CausesValidation取消按钮的属性设置为false

回答by Brandon

Set the CausesValidationproperty to false.

CausesValidation属性设置为false

回答by Joe

Judicious use of the Control.CausesValidationproperty will help you achieve what you want.

明智地使用该Control.CausesValidation财产将帮助您实现您想要的。

回答by Daniel Schaffer

If the validation occurs when the edit box loses focus, nothing about the the cancel button is going to stop that from happening.

如果在编辑框失去焦点时进行验证,则取消按钮不会阻止这种情况发生。

However, if the failing validation is preventing the cancel button from doing its thing, set the CausesValidationproperty of the button to false.

但是,如果失败的验证阻止取消按钮执行其操作,请将CausesValidation按钮的属性设置为false

Reference: Button.CausesValidationproperty

参考:Button.CausesValidation财产

回答by Vimal Raj

Obviously CausesValidationproperty of the button has to be set to false and then the validating event will never happen on its click. But this can fail if the parent control of the button has its CausesValidationProperty set to true. Most of the time developers misses/forgets to change the CausesValidationproperty of the container control (like the panel control). Set that also to False. And that should do the trick.

显然CausesValidation,按钮的属性必须设置为 false,然后验证事件将永远不会在单击时发生。但是,如果按钮的父控件将其CausesValidation属性设置为 true,这可能会失败。大多数情况下,开发人员会错过/忘记更改CausesValidation容器控件(如面板控件)的属性。也将其设置为 False。这应该可以解决问题。

回答by Steve Sheldon

Setting CausesValidation to false is the key, however this alone is not enough. If the buttons parent has CausesValidation set to true, the validating event will still get called. In one of my cases I had a cancel button on a panel on a form, so I had to set CausesValidation = false on the panel as well as the form. In the end I did this programatically as it was simpler than going through all the forms...

将 CausesValidation 设置为 false 是关键,但仅此是不够的。如果按钮父级的 CausesValidation 设置为 true,则仍将调用验证事件。在我的一个案例中,我在表单的面板上有一个取消按钮,所以我必须在面板和表单上设置 CausesValidation = false。最后我以编程方式完成了这项工作,因为它比浏览所有表格更简单......

Control control = cancelButton;

while(control != null)
{
   control.CausesValidation = false;
   control = control.Parent;
}

回答by Ben

I was having problems getting my form to close, since the validation of certain controls was stopping it. I had set the control.CausesValidation = falsefor the cancel button and all the parents of the cancel button. But still was having problems.

我在关闭表单时遇到问题,因为某些控件的验证正在阻止它。我已经设置了control.CausesValidation = false取消按钮和取消按钮的所有父项。但是还是遇到了问题。

It seemed that if the user was in the middle of editing a field that was using validation and just decided to give up (leaving the field with an invalid input), the cancel button event was being fired but the window would not close down.

似乎如果用户正在编辑正在使用验证的字段并刚刚决定放弃(留下无效输入的字段),则会触发取消按钮事件,但窗口不会关闭。

This was fixed by the following in the cancel button click event:

这是通过取消按钮单击事件中的以下内容修复的:

private void btnCancel_Click(object sender, EventArgs e)
{
    // Stop the validation of any controls so the form can close.
    AutoValidate = AutoValidate.Disable;
    Close();
}

回答by Olivier de Rivoyre

In complement of the answer of Daniel Schaffer: if the validation occurs when the edit box loses focus, you can forbid the button to activateto bypass local validation and exit anyway.

作为 Daniel Schaffer 回答的补充:如果在编辑框失去焦点时发生验证,您可以禁止按钮激活以绕过本地验证并退出。

public class UnselectableButton : Button
{
    public UnselectableButton()
    {
        this.SetStyle(ControlStyles.Selectable, false);
    }
}

or if you use DevExpress:

或者如果您使用 DevExpress:

this.simpleButtonCancel.AllowFocus = false;

Note that doing so will change the keyboard experience: the tab will focus anymore on the cancel button.

请注意,这样做会改变键盘体验:选项卡将再次聚焦在取消按钮上。

回答by Wade Hatler

None of these answers quite did the job, but the last answer from this threaddoes. Basically, you need to:

这些答案都没有完成这项工作,但该线程的最后一个答案确实如此。基本上,您需要:

  1. Insure that the Cancel button (if any) has .CausesValidation set to false
  2. Override this virtual method.

    protected override bool ProcessDialogKey(Keys keyData) {
        if (keyData == Keys.Escape) {
            this.AutoValidate = AutoValidate.Disable;
            CancelButton.PerformClick();
            this.AutoValidate = AutoValidate.Inherit;
            return true;
        }
        return base.ProcessDialogKey(keyData);
    }
    
  1. 确保取消按钮(如果有)将 .CausesValidation 设置为 false
  2. 覆盖这个虚拟方法。

    protected override bool ProcessDialogKey(Keys keyData) {
        if (keyData == Keys.Escape) {
            this.AutoValidate = AutoValidate.Disable;
            CancelButton.PerformClick();
            this.AutoValidate = AutoValidate.Inherit;
            return true;
        }
        return base.ProcessDialogKey(keyData);
    }
    

I didn't really answer this, just pointing to the two guys who actually did.

我并没有真正回答这个问题,只是指着实际回答的两个人。

回答by Adiono

Maybe you want to use BackgroundWorker to give little bit delay, so you can decide whether validation should run or not. Here's the example of avoiding validation on form closing.

也许您想使用 BackgroundWorker 来提供一点延迟,以便您可以决定是否应该运行验证。这是避免表单关闭验证的示例。

    // The flag
    private bool _isClosing = false;

    // Action that avoids validation
    protected override void OnClosing(CancelEventArgs e) {
        _isClosing = true;
        base.OnClosing(e);
    }

    // Validated event handler
    private void txtControlToValidate_Validated(object sender, EventArgs e) {           
        _isClosing = false;
        var worker = new BackgroundWorker();
        worker.DoWork += worker_DoWork;
        worker.RunWorkerAsync();
        worker.RunWorkerCompleted += worker_RunWorkerCompleted;
    }

    // Do validation on complete so you'll remain on same thread
    void worker_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e) {
        if (!_isClosing)
            DoValidationHere();
    }

    // Give a delay, I'm not sure this is necessary cause I tried to remove the Thread.Sleep and it was still working fine. 
    void worker_DoWork(object sender, DoWorkEventArgs e) {
        Thread.Sleep(100);
    }