1

I am loading a form via ajax and usind the new .on() to load the jQuery validate plugin is not loaded before I press the submit a second time. I understand why I think. The on() function loads the validate on the form when I press submit. Is there any way to fix this? Before I was using livequery but that does not work with jQuery 1.9.1 or at least is not recommended. Here is my code:

 $(document)
.on("submit",function(event){
$("#myform").validate();
    event.preventDefault();
  })

This code worked before in jQuery 1.4.2

 $("#myform")
.livequery(function(){
$(this).validate():
  })

So what happens now is the form is not submitted but the errors only show when I press submit a second time.

update: Thanks for new insight Sparky! I am used to livequery in earlier jQuery versions. But I understand that livequery is constantly listening for the element and puts CPU load on the client. Your code on jsfiddle does exactly what I want!

So I should not use .on() on the generated form? Instead run the validate() on the form in the callback. This code works (inside document.ready of course):

$("#ask").click(function(){
     //send postdata from inputs, returns form with filled fields (defined with jQuery selectors)
    $.post("include_form.lasso",{zip:zip,custno:custno},function(data){
    // div"skjema" is filled with form with ID  
$("#skjema").html(data);
})
    .done(function() { $("#myform").validate();});
})

I have a lot of extras in the validate() that is not shown here. I haven't tested this but I guess it will work. Is it better to use .ajax() instead of my .post() code here? What I do is - when the link is clicked send the two field zip and custno to "include_form.lasso" - fill the result in the "skjema" DIV. This is a form - attach the validate() function to the generated form - I do not need a stopPropogation() on the form to prevent default submit? It should validate first?

Update: After great help from Sparky here is what works: Just wanted to share my code. I needed 2 functions for my dynamic form, validate() and autocomplete(). So I put the validate() code and the autocomplete in 2 functions:

function pumpemod(){ 
$("#pumpemod").autocomplete({
source: "code/sql2.php?mod=1",
minLength: 3,
delay: 400}); }

function send_validate() { $("#my_dropdown").validate()...}

So in the .on() code I call the functions. When I click a radio button it fetches a form. It looks like this:

$(document)
    .on('click','input.montRadio',function(event){
    var pnr = $("#postnr").val();
    var knr = $(this).attr("rel");
   $.post("code/vis_skjema.lasso",{postnr:pnr,kundenr:knr},function(data){
        $("#skjema").html("/images/loading.gif");
        $("#skjema").html(data);
        pumpemod();
        send_validate();
    });

    });

Hopes this can help someone else. At least I got a good understanding now of on(). I wanted to move from livequery to on().

asle
  • 165
  • 1
  • 3
  • 13

5 Answers5

2

The on() function loads the validate on the form when I press submit. ... So what happens now is the form is not submitted but the errors only show when I press submit a second time.

You are correct. The plugin is not initialized on your form until you click submit the first time. This is because, with on(), you are simply attaching the plugin's initialization function to a submit event. No matter how you do this, delegate, bind, etc., your problem will be the same... you'll never properly initialize the plugin until after that first click.

So what happens now is the form is not submitted

Your preventDefault() is blocking the normal submit. You need to get rid of all this and simply call .validate() immediately after you construct the form's HTML.

Is there any way to fix this?

You must initialize the plugin (one time) immediately after you load the form with your ajax. Where is the code that does this? Try putting your .validate() function inside of the complete callback function of the ajax that loads your form. This will run .validate() once upon completion of the ajax.

Or if you use jQuery .load()...

$('#content').load('form_loader', function() {
    ('#myform').validate(); // initialize plugin after form is loaded
});

Without seeing your ajax code, the crude demo below was quickly constructed to only simulate this concept. Click the "test" button to load a form with ajax, which then initializes .validate() upon completion.

http://jsfiddle.net/dUmfK/

You can see the form is loaded into a div and ready to validate before the very first click.

Sparky
  • 98,165
  • 25
  • 199
  • 285
  • I commented your reply in the original answer. If I understand I don't need an .on() function for this? – asle Mar 28 '13 at 10:27
  • @asle, you understand correctly. However, remember my answer is only focused on proper initialization of the plugin on the form. – Sparky Mar 28 '13 at 14:55
  • Not sure what you mean. Is it good practice to initialize validate() when the specific form is loaded? I usually use .on() on dynamic elements but .on() requires an event and that was not what I wanted to trigger the function. – asle Mar 28 '13 at 23:59
  • @asle, I was just trying to be clear about my answer... that it's only about handling plugin initialization after you load the form with `ajax`... not about how to handle any `ajax` for submission of the form data. This may not have been entirely clear to the reader. Yes, since `.validate()` is just a "one-time" plugin initialization, it **must** occur _after_ the form is created, and also _before_ you need to have validation available. For most people, this is upon the DOM `ready` event. For you, it's immediately after you create/load the form's HTML. – Sparky Mar 29 '13 at 00:13
  • thanks for clarifying. I really appreciate your time and insight :-) – asle Mar 29 '13 at 13:00
0

I think you have a mispelling..

Working example: http://jsfiddle.net/mFeww/4/

     $(document).ready(function(){
        $("#formID").on("submit",function(event){
            $("#myform").validate();
            event.preventDefault();
      })
});

HTML:

<form id="formID">

</form>
What have you tried
  • 11,018
  • 4
  • 31
  • 45
  • How is this any different? As you can see, [your jsFiddle has the exact same problem as the OP is describing... no validation until after the submit button is clicked twice.](http://jsfiddle.net/mFeww/5/) That's because the plugin is not initialized on the form until the submit button is clicked the first time. ( This is a very popular misconception. ) You **must** _initialize_ the plugin (only ONCE) _before_ the button is first clicked. – Sparky Mar 28 '13 at 03:41
0

You need to add a selector in the call to on to make a delegate instead of a regular bind:

$(document).on("submit", "#myform" function(event){
  $(this).validate();
  event.preventDefault();
});

If possible, bind the delegate to an element closer to the form than the entire document.

Guffa
  • 687,336
  • 108
  • 737
  • 1,005
  • The problem is still that you must "submit" before the validate() is run. Sparky is correct. – asle Mar 28 '13 at 09:14
  • 2
    @asle: Aha, the `validate` method doesn't validate, it only adds validation. Yes, then you need to call it on the form as soon as it exists. – Guffa Mar 28 '13 at 10:05
0

Per my comment

 $(document).ready(function(){
  $("#myform").on("submit",function(){
   $(this).validate();
  return false;
 });
});
Jay Rizzi
  • 4,196
  • 5
  • 42
  • 71
0

I had something similar. here is how I resolved it.

I had the same issue: my goal: validate many forms with the same class:

my php:

form class="js-validate-itemForm" method="post" action="">
...
form class="js-validate-itemForm" method="post" action="">

my js:

$('.js-validate-itemForm').each(function () {
       $(this).validate({
           submitHandler: function (form, event) { 
               doActionOnItemform(form, event);
               return false;
           }
        });
    });
Olivier Royo
  • 810
  • 10
  • 13