2

I'm looping through a marker layer in a Leaflet map to catch the latitude and longitude of each marker and sending this coordinates in my database with Ajax.

Then, when I've sent the latitude and longitude of each marker in my database, I want to call my WFS layer with another Ajax to show the new markers added to my db.

For that, I want to call my second Ajax afther the first one has finished, so I tried to use $.when().done(), but it doesn't works.

If I'm sending the coordinates of a few markers, it works, but if I try sending 200 markers, the second Ajax is executed before the end of the first one, and my WFS layer is not displayed. If I set a timeout on se second Ajax to give time to the first Ajax to execute, it works, but it's not a solution.

Here is my code :

var dialog_create = $('#dialog_create').dialog();
dialog_create.dialog(options, {
  buttons: {
    Add: function() {
      $.when(
        layer.eachLayer(function(layer) {
          latGPS = layer.getLatLng().lat;
          lngGPS = layer.getLatLng().lng;

          $('#latitudeEP').val(latGPS);
          $('#longitudeEP').val(lngGPS);

          data = $("#formulaireEP").serialize();

          $.ajax({
            url: 'assets/php/create/create_EP.php',
            type: $("#formulaireEP").attr('method'),
            data: data,
            success: function() {
              dialog_create_EP.dialog("close");
              $("#formulaireEP")[0].reset();
            }
          })
        })
      ).done(function(data) {
        //setTimeout(function(){
        $.ajax({
          url: owsrootUrlAssainissement + L.Util.getParamString(parametersEP),
          dataType: 'jsonp',
          jsonpCallback: 'callEP'
        }).done(EPvannes1);
        //},5000);
      });
      return false;
    },
    Cancel: function() {
      dialog_create_EP.dialog("close");
    },
  }
});
dialog_create_EP.dialog("open");

EDIT :

Here is my best attempt using a deffered object, but it doesn't works...

var dialog_create = $('#dialog_create').dialog();
dialog_create.dialog(options, {
  buttons: {
    Add: function() {
    var defer = $.Deferred();

      function getAjaxDeffered(){
        layer.eachLayer(function(layer) {
          latGPS = layer.getLatLng().lat;
          lngGPS = layer.getLatLng().lng;

          $('#latitudeEP').val(latGPS);
          $('#longitudeEP').val(lngGPS);

          data = $("#formulaireEP").serialize();

          $.ajax({
            url: 'assets/php/create/create_EP.php',
            type: $("#formulaireEP").attr('method'),
            data: data,
            success: function() {
              dialog_create_EP.dialog("close");
              $("#formulaireEP")[0].reset();
            }
          })
        })
      }

      defer.resolve(getAjaxDeffered());

      $.when(defer).then(function(data) {
        //setTimeout(function(){
        $.ajax({
          url: owsrootUrlAssainissement + L.Util.getParamString(parametersEP),
          dataType: 'jsonp',
          jsonpCallback: 'callEP'
        }).done(EPvannes1);
        //},5000);
      });
      return false;
    },
    Cancel: function() {
      dialog_create_EP.dialog("close");
    },
  }
});
dialog_create_EP.dialog("open");
Hippipers
  • 113
  • 2
  • 10
  • 1
    This answer will help you http://stackoverflow.com/a/39679275/6608101 – Mohit Tanwani Oct 05 '16 at 09:05
  • Execute your second ajax call under the success function of first – Nitin Dhomse Oct 05 '16 at 09:07
  • As my first layer is in layer.eachLayer, I can't execute the second Ajax under the sucess function of the first one or my second Ajax will be called each time I'm sending a marker in my database I guess – Hippipers Oct 05 '16 at 09:17
  • 1
    @Loading.. Thanks, I think using Deffered object can indeed fix my problem. I will have a look and try to understand how it works :-) – Hippipers Oct 05 '16 at 09:27
  • @Loading.. Sorry, I've edited my code trying to use a deffered object but it still not works althought I think I'm using this method the bad way – Hippipers Oct 05 '16 at 11:21

2 Answers2

1

Looks like your layer.eachLayer function does not return a Promise/Deferred. Along jQuery doc:

If a single argument is passed to jQuery.when() and it is not a Deferred or a Promise, it will be treated as a resolved Deferred and any doneCallbacks attached will be executed immediately.

ptrk
  • 1,800
  • 1
  • 15
  • 24
1

Ok, so I found the solution thanks to this post : jquery deferred in .each loop

Here is my final code for posterity ;-) :

var dialog_create = $('#dialog_create').dialog();
dialog_create.dialog(options, {
  buttons: {
    Add: function() {
 
      function getAjaxDeffered(){

      var promises = [];

        layer.eachLayer(function(layer) {

        var def = new $.Deferred (); 

          latGPS = layer.getLatLng().lat;
          lngGPS = layer.getLatLng().lng;
 
          $('#latitudeEP').val(latGPS);
          $('#longitudeEP').val(lngGPS);
 
          data = $("#formulaireEP").serialize();
 
          $.ajax({
            url: 'assets/php/create/create_EP.php',
            type: $("#formulaireEP").attr('method'),
            data: data,
            success: function() {
              def.resolve();
              dialog_create_EP.dialog("close");
              $("#formulaireEP")[0].reset();
            }
          })
          promises.push(def)
        })
      return $.when.apply(undefined, promises).promise();
      }
 
      defer.resolve(getAjaxDeffered());
 
      getAjaxDeffered().then(function(data) {
        $.ajax({
          url: owsrootUrlAssainissement + L.Util.getParamString(parametersEP),
          dataType: 'jsonp',
          jsonpCallback: 'callEP'
        }).done(EPvannes1);
      });
      return false;
    },
    Cancel: function() {
      dialog_create_EP.dialog("close");
    },
  }
});
dialog_create_EP.dialog("open");
Community
  • 1
  • 1
Hippipers
  • 113
  • 2
  • 10