jQuery .validate() submitHandler 不触发

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/30720354/
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-26 16:44:01  来源:igfitidea点击:

jQuery .validate() submitHandler not firing

jqueryjquery-validatebootbox

提问by david-l

I'm loading a dialog box with a form that's built on-the-fly using Bootbox.jsand I'm validating user input with a jQuery validate plugin.

我正在加载一个对话框,其中包含一个使用Bootbox.js即时构建的表单,我正在使用 jQuery 验证插件验证用户输入。

Validation works just fine, but the submitHandleris ignored when the form is filled in successfully.

验证工作正常,但submitHandler在成功填写表单时会被忽略。

What's going wrong?

怎么了?

submitHandler: function(form) {
    alert("Submitted!");
    var $form = $(form);
    $form.submit();
}

See the full example below. I've looked at other posts where a similar issue has been raised. Unfortunately they seem to have the form rendered on the page whereas I'm rendering my via jQuery.

请参阅下面的完整示例。我查看了其他帖子,其中提出了类似的问题。不幸的是,他们似乎在页面上呈现了表单,而我正在通过 jQuery 呈现我的表单。

$(document).on("click", "[data-toggle=\"contactAdmin\"]", function() {
  bootbox.dialog({
    title: "Contact admin",
    buttons: {
      close: {
        label: 'Close',
        className: "btn btn-sm btn-danger",
        callback: function() {}
      },
      success: {
        label: "Submit",
        className: "btn btn-sm btn-primary",
        callback: function() {
          $("#webteamContactForm").validate({
            rules: {
              requestType: {
                required: true
              }
            },
            messages: {
              requestType: {
                required: "Please specify what your request is for",
              }
            },
            highlight: function(a) {
              $(a).closest(".form-group").addClass("has-error");
            },
            unhighlight: function(a) {
              $(a).closest(".form-group").removeClass("has-error");
            },
            errorElement: "span",
            errorClass: "help-blocks",
            errorPlacement: function(error, element) {
              if (element.is(":radio")) {
                error.appendTo(element.parents('.requestTypeGroup'));
              } else { // This is the default behavior 
                error.insertAfter(element);
              }
            },
            submitHandler: function(form) {
              alert("Submitted!");
              var $form = $(form);
              $form.submit();
            }
          }).form();
          return false;
        }
      }
    },
    message: '<div class="row">  ' +
      '<div class="col-md-12"> ' +
      '<form id="webteamContactForm" class="form-horizontal" method="post"> ' +
      '<p>Please get in touch if you wish to delete this content</p>' +
      '<div class="form-group"> ' +
      '<div class="col-md-12"> ' +
      '<textarea id="message" name="message" class="form-control input-md" rows="3" cols="50">This email is to notify you the creator is putting a request for the following item\n\n' +
      this.attributes.getNamedItem("data-url").value + '\n\n' + '</textarea> ' +
      '<span class="help-block">Feel free to change the message and add more information. Please ensure you always provide the link.</span> </div> ' +
      '</div> ' +
      '<div class="form-group requestTypeGroup"> ' +
      '<label class="col-md-4 control-label" for="requestType">This request is for:</label> ' +
      '<div class="col-md-4"> <div class="radio"> <label for="Edit"> ' +
      '<input type="radio" name="requestType" id="requestType-0" value="Edit"> ' +
      'Editing </label> ' +
      '</div><div class="radio"> <label for="Delete"> ' +
      '<input type="radio" name="requestType" id="requestType-1" value="Delete"> Deletion</label> ' +
      '</div> ' +
      '</div> </div>' +
      '</form> </div>  </div>'
  });
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.0/jquery.min.js"></script>
<script src="//cdnjs.cloudflare.com/ajax/libs/bootbox.js/4.4.0/bootbox.min.js"></script>
<link href="https://maxcdn.bootstrapcdn.com/bootstrap/3.2.0/css/bootstrap.min.css" rel="stylesheet" />
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.2.0/js/bootstrap.min.js"></script>
<script src="https://ajax.aspnetcdn.com/ajax/jquery.validate/1.13.0/jquery.validate.js"></script>

<a data-toggle="contactAdmin" data-title="help" data-url="http:/www.mydomain.com/some-url" href="#">Contact Web team</a>

View on jsFiddle

在 jsFiddle 上查看

回答by Sparky

Inspecting the DOM of the jsFiddle and two problems become apparent.

检查 jsFiddle 的 DOM 和两个问题变得明显。

  1. Your "submit" <button>is a type="button".

  2. Your "submit" button is outside of the <form></form>container.

  1. 您的“提交”<button>是一个type="button".

  2. 您的“提交”按钮位于<form></form>容器之外。

If you want the jQuery Validate plugin to automatically capture the clickevent of the "submit" button...

如果您希望 jQuery Validate 插件自动捕获click“提交”按钮的事件...

  • the button must be a type="submit"
  • The button must be within the <form></form>container.
  • 按钮必须是 type="submit"
  • 按钮必须在<form></form>容器内。

These two conditions must be met if you want the plugin to operate as intended.

如果您希望插件按预期运行,则必须满足这两个条件。



You've also incorrectly placed the .validate()method within the successcallback of your modal dialog box "submit" button.

您还错误地将该.validate()方法放置在success模态对话框“提交”按钮的回调中。

The .validate()method is only used for initializingthe plugin and should be called onceafter the form is created.

.validate()方法仅用于初始化插件,应在表单创建后调用一次



EDIT:

编辑

After playing around with this, it becomes apparent that the Bootbox modal pluginmay have some critical limitations that interfere with the submission of the form.

在玩弄这个之后,很明显,Bootbox 模态插件可能有一些严重的限制,会干扰表单的提交。

  1. I am initializing the Validate plugin afterthe dialog is opened.

  2. I am using the .valid()method within the "submit" to trigger the validation test.

  1. 打开对话框,我正在初始化验证插件。

  2. 我正在使用.valid()“提交”中的方法来触发验证测试。

I can get validation initialized and working as it should, but the dialog is dismissed before the actual form submission takes place. Perhaps there is a solution, but after reviewing the documentation for Bootbox, it's not readily apparent.

我可以初始化验证并按原样工作,但在实际提交表单之前对话框被关闭。也许有一个解决方案,但在查看了 Bootbox 的文档后,它并不明显。

https://jsfiddle.net/vyaw3ucd/2/

https://jsfiddle.net/vyaw3ucd/2/



EDIT 2:

编辑2:

As per the OP's solution...

根据OP的解决方案...

bootbox.dialog({
    // other options,
    buttons: {
        success: {
            label: "Submit",
            className: "btn btn-sm btn-primary",
            callback: function () {
                if ($("#webteamContactForm").valid()) {
                    var form = $("#webteamContactForm");
                    form.submit();  // form submits and dialog closes
                } else {
                    return false;  // keeps dialog open
                }
            }
        }
    }
});

However, by simply using the supplied formargument directly, you do not have any errors when using the submitHandleroption of the jQuery Validate plugin.

但是,通过直接使用提供的form参数,在使用submitHandlerjQuery Validate 插件选项时不会出现任何错误。

submitHandler: function (form) {
    console.log("Submitted!");
    form.submit();
}

DEMO: https://jsfiddle.net/vyaw3ucd/5/

演示:https: //jsfiddle.net/vyaw3ucd/5/

回答by david-l

Thanks Sparky for your help, the solution your provided gave me the answer. It seems having the submitHandler causes some confusion for the submit logic.

感谢 Sparky 的帮助,您提供的解决方案给了我答案。似乎有 submitHandler 导致提交逻辑有些混乱。

I removed the submitHandler and added the following to success callback and everything works as expected

我删除了 submitHandler 并将以下内容添加到成功回调中,一切都按预期进行

success: {
         label: "Submit",
         className: "btn btn-sm btn-primary",
         callback: function () {
             if($("#webteamContactForm").valid()){
                    var form = $("#webteamContactForm");
                    form.submit();
                } else {
                    return false;
                }
         }
    }

回答by yardpenalty.com

I know this is an old post but I thought I would share my resolve to a similar problem. I could not get my form to submit by pressing enter but I could get it to validate on enter. So I used the chaining method and now I can submit my form on enter.

我知道这是一篇旧帖子,但我想我会分享我对类似问题的决心。我无法通过按 Enter 来提交我的表单,但我可以让它在输入时进行验证。所以我使用了链接方法,现在我可以在输入时提交我的表单。

jQuery:

jQuery:

  //Variables created without the keyword var, are always global, even if they are created inside a function.
    var form = $('#<?echo $PAGEID?>');
    var FormError = $('.alert-danger',form);
    var success = $('.alert-success',form);

     form.keypress(function(e){
         if(e.which == 13){ //TRIGGER SUBMIT THROUGH ENTER      
             document.getElementById('defaultActionButton').click(); 
         }
     }).validate({
        focusInvalid: false, // do not focus the last invalid input
        onkeyup: false, 
        ignore: ".ignore", //required for hidden input validation ie: hiddenRecaptcha
        rules:{
            "TYPE": {
                required: true,     
            },
            "MSG": {
                required: true,
                rangelength:[40,1000]
            },
            "CONTACT": {
                 required: {
                     depends: "#newuser:checked"
                 }
            },
            "EMAIL": {
                 required: true,
                 email: {
                    depends: function() {
                        if(!$("#newuser:checked"))
                            return true;
                        else
                            return false;
                    }
                 },
                 HTH_TelephoneEmail: {
                        depends: function() {
                            if($("#newuser:checked"))
                                return true;
                            else
                                return false;
                        }
                     }
            },          
            hiddenRecaptcha: {
                required: function () {
                    if (grecaptcha.getResponse() == '') {
                        return true;
                    } else {
                        return false;
                    }
                }
            }
        },
        messages: { // custom messages for form validation input
               "TYPE": {
                    required: 'Please select an option as it pertains to your inquiry'
               },
               "MSG": {
                    required: 'Please provide some content as it pertains to your inquiry'       
               },
               "CONTACT": {
                required: "Please enter a contact person or company"
               },
              hiddenRecaptcha: {
                required: function() {
                    $(".g-recaptcha:first").tooltip("enable").tooltip("show");
                }
              }
        },
        showErrors: function(errorMap, errorList) {
            // Clean up any tooltips for valid elements
            $.each(this.validElements(), function (index, element) {
                element = $(element);
                NoError_ToolTip(element);
            });
            // Create new tooltips for invalid elements
            $.each(errorList, function (index, error) {
                element = $(error.element);
                message = error.message;
                Error_ToolTip(element,message);
            });
        },                  
        invalidHandler: function (event, validator) { //display error alert on form submit     
            success.hide();
            $(document).scrollTop( $(".form-body").offset().top ); 
        },
         submitHandler: function () { 
       Submit_Complete(); //fires ajax call
   }
    });

回答by Reimi Beta

You should change the name for your submit button, because you have a naming conflict. For example, try changing it from name="submit"to name="other".

您应该更改提交按钮的名称,因为您有命名冲突。例如,尝试将其从 更改name="submit"name="other"