Question

I'm having a JavaScript issue where I need a function to run and complete before another function is run.

Here's the code I need to run and complete first. As you can see, I'm looping through all address input fields in the form and geocoding them through the Google Maps API.

  $('#form input:text.address').each(function() {
    var address = $(this);
    var Geocoder = new google.maps.Geocoder();

    Geocoder.geocode({ 'address': address.val() }, function(results, status) {
      // Store the results in a hidden input field.
    });
  });

After this fully completes — that is, after all the responses from the Google Maps API have returned — I then need the form to submit. Here's the current ajax submit code I use:

  $('#form').ajaxForm(
    {
      success:
        function() {
          ...
        }
    }
  );

The problem I'm having is the form is submitted before the Google Maps API has responded. The ajaxForm() method allows a beforeSubmit callback function, but that still does not wait for the function to complete. I realize this is because JavaScript is asynchronous, but I'm unsure how to solve this particular issue.

Any help is appreciated! Thanks!

Was it helpful?

Solution

Call the form submit from the success handler of Geocoder.geocode. Since you have many calls to the same function, set an indicator to indicate when the last call is finished and then submit the form.

Here is one way...

var count = $('#form input:text.address').size();
$('#form input:text.address').each(function() {
    var address = $(this);
    var Geocoder = new google.maps.Geocoder();

    Geocoder.geocode({ 'address': address.val() }, function(results, status) {
      // Store the results in a hidden input field.
      count--;
      if (count === 0) {
          //submit form here!
      }
    });
  });

OTHER TIPS

I don't know JQuery, so please forgive me if I'm off base, but it seems to me that you can solve your problem by submitting the form inside the geocode results handler (where it says // Store the results in a hidden input field.) instead of from that other success handler (which I gather is supposed to be called when an AJAX query succeeds?). Is there something preventing you from doing it that way?

The problem is that the form can still be submitted before all Google-functions have loaded their data? Then we need to disable the submit buttons from the start, load all the data, and then enable the forms again after it has completed loading.

Uing chetan-sastry's solution to check for when form has loaded things should look something like this.

var count = $('#form input:text.address').size();

$('#form input:text.address').each(function() {
  var address = $(this);
  var Geocoder = new google.maps.Geocoder();

  Geocoder.geocode({ 'address': address.val() }, function(results, status) {
    // Store the results in a hidden input field.

      count--;
      if (count === 0) {
         $('#form').ajaxForm( /* ... */);
         $('#form input:submit').attr('disabled', '0'); // Enable submit-buttons
      }
  });
});

Then to prevent the user to submit the form before stuff has been loaded you should set the submit to disabled when the page is loading.

<input type="submit" disabled="1" />
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top