2016-04-08 5 views
1

У меня есть вид позвоночника с некоторой проверкой формы. Проверка формы использует preventDefault, если форма имеет ошибки. Если это не так, оно должно принять значение в поле ввода, извлечь lat, lng и заполнить два скрытых поля, прежде чем отправить будет разрешено продолжить. Я пытаюсь использовать отложенную, но не уверен, что у меня получилось не так. Я вырезал некоторые ненужные биты здесь и там, чтобы сделать его более чистым, чтобы публиковать здесь.Выполнение и завершение геокодирования google maps перед тем, как разрешить отправку для продолжения.

Я пробовал использовать preventDefault с отложенным (что мне не нужно было бы в любом случае исправлять?), Но повторное отправление - это немного сложная задача с использованием события submit.

Без предупреждения, поля lat, lng не обновляются перед подачей. Возможно, неправильная реализация отложенных/обещаний или при использовании preventdefault submit снова запускает проверку, и я заканчиваю цикл. Я не хочу использовать setTimeout, потому что я не хочу задерживать пользователя дольше, чем получать ответ.

events: { 
    'submit': 'validateForm' 
}, 
validateForm: function(e){ 

//lotsa validation then 

    var loc = $('#location').length; 
    if (loc){ 
    var parent = $(e.currentTarget).closest('form'); 
    e.preventDefault(); 
    $.when(this.getCoordinates(e)) 
    .done(function(){ 
     parent.submit(); 
    }); 
    } 
}, 

getCoordinates : function(e) { 
    var deferred = $.Deferred(); 
    var that = this; 
    var parent = $(e.currentTarget).closest('form'); 
    var addr = parent.find('#location').val(); 

    if ($.trim(addr).length) { 
     var apiurl = '//maps.googleapis.com/maps/api/geocode/json?address=' + addr '&bounds=' + bounds + ''; 
     $.ajax({ 
      url : apiurl, 
      dataType : 'json' 
     }) 
     .done(function (data) { 

      try { 
       if(!data.results.length){ 
        return; 
       } 
       var coord = data.results[0].geometry.location; 
       var result = data.results[0].formatted_address; 
       if (coord) { 
        var lat = coord.lat; 
        var lon = coord.lng; 

        parent.find("input[data-geo-type = 'lat']").val(lat); 
        parent.find("input[data-geo-type = 'lng']").val(lon); 
        deferred.resolve(); 
       } 

      } catch (e) { 
       console.error(e); 
      } 
     }).fail(function() { 
      $(e.currentTarget).val(addr); 
     }); 
    } else { 
     deferred.reject(); 
    } 
return deferred.promise(); 
}, 

Любая помощь или указатели оценили!

+0

Ваша проблема: 'validateForm' не запускать форму submit? или что-то другое? Что такое 'submitCoordinates' здесь? –

+0

'submitCoordinates()' или 'getCoordinates()'? Также фигурные скобки не сбалансированы. Исправьте вопрос, может быть, кто-то может дать ответ. –

+0

Исправлено имя метода и скобка. Без preventdefault поля lat, lng не обновляются до отправки. Возможно, неправильная реализация отложенных/обещаний или при использовании preventdefault submit снова запускает проверку, и я заканчиваю цикл. Я не хочу использовать setTimeout, потому что я не хочу задерживать пользователя дольше, чем получать ответ. Спасибо, –

ответ

1

Похоже, вы, вероятно, столкнулись с бесконечным циклом из-за своего внутреннего parent.submit(). Поскольку parent является объектом jQuery, он запускает все события, что приводит к повторному запуску ajax, бесконечно. К счастью, решение прост. Вместо вызова .submit() на объект jQuery вызовите его в самой форме. Вы также должны убедиться, что у вас нет id="submit" в любом месте. Вызывая его непосредственно в форме, вы просто отправляете форму, не вызывая никаких событий.

validateForm: function(e){ 

//lotsa validation then 

    var loc = $('#location').length; 
    if (loc){ 
    var parent = $(e.currentTarget).closest('form'); 
    e.preventDefault(); 
    $.when(this.getCoordinates(e)) 
    .done(function(){ 
     //parent.submit(); 
     parent[0].submit();/* modified line */ 
    }); 
    } 
},