2016-01-06 2 views
1

Я пытаюсь отобразить некоторые данные, когда пользователь прокручивает страницу вниз, но вызов ajax выполняется как минимум 2 раза, а иногда и 4 раза. Есть ли способ выполнить вызов ajax только один раз? Благодарю.Событие срабатывает несколько раз, когда я прокручиваю страницу вниз

$(window).scroll(function() { 
     if ($(document).height() <= $(window).scrollTop() + $(window).height()) { 
       $.ajax({ 
       type : "POST", 
       url : $('#AjaxMoreStatus').attr("data-url"), 
       dataType : "HTML", 
       beforeSend: function() { 
        $('.spinner').show(); 
       }, 
       complete: function() { 
        $('.spinner').hide(); 
       }, 
       success : function (data) { 
        $('#AjaxMoreStatus').append(data); 
       } 
      }); 
     } 
    }); 
+0

Использование имени SetTimeout с clearTimeout. – Jai

+0

Не могли бы вы просто создать переменную 'bool', а затем просто измените значение' bool', когда они прокрутили, чтобы вы больше не пытались выполнить вызов ajax. – Canvas

+0

@Canvas Я не уверен, что 'bool' будет правильным. –

ответ

4

При использовании .scroll() события и когда window прокручиваются, это увольняет несколько раз. Это ожидаемое поведение. Лучший способ заключается в использовании таймер для как 500ms и ждать браузера, чтобы остановить прокрутку:

var tmr = 0; 
$(window).scroll(function() { 
    clearTimeout(tmr); 
    $('.spinner').show(); 
    tmr = setTimeout(function() { 
    if ($(document).height() <= $(window).scrollTop() + $(window).height()) { 
     $.ajax({ 
     type : "POST", 
     url : $('#AjaxMoreStatus').attr("data-url"), 
     dataType : "HTML", 
     beforeSend: function() { 
      $('.spinner').show(); 
     }, 
     complete: function() { 
      $('.spinner').hide(); 
     }, 
     success : function (data) { 
      $('#AjaxMoreStatus').append(data); 
     } 
     }); 
    } 
    }, 500); 
}); 

Это также сохранить AJAX опрос на сервере слишком много раз. Вы также можете взять содержимое beforeSend() в верхней части вызова и таймера AJAX.

+0

Спасибо! Вы действительно поняли, и код работает. –

0

Ну, это известная проблема, и ее решает метод, называемый debouncing logic.

Что такое Debouncing logic: which Возвращает функцию, которая до тех пор, пока она будет вызываться, не будет запущена. Функция будет вызвана после того, как она перестанет вызываться для N миллисекунд. Если отправлено немедленно, передается, запускается функция на переднем фронте, а не в конце.


дребезга логика:

// Returns a function, that, as long as it continues to be invoked, will not 
// be triggered. The function will be called after it stops being called for 
// N milliseconds. If `immediate` is passed, trigger the function on the 
// leading edge, instead of the trailing. 
function debounce(func, wait, immediate) { 
    var timeout; 
    return function() { 
    var context = this, args = arguments; 
    var later = function() { 
     timeout = null; 
     if (!immediate) func.apply(context, args); 
    }; 
    var callNow = immediate && !timeout; 
    clearTimeout(timeout); 
    timeout = setTimeout(later, wait); 
    if (callNow) func.apply(context, args); 
    }; 
}; 

//target code/callback to be called on scroll/resize event 
function callback() { 
    clearTimeout(tmr); 
    $('.spinner').show(); 
    tmr = setTimeout(function() { 
    if ($(document).height() <= $(window).scrollTop() + $(window).height()) { 
     $.ajax({ 
     type : "POST", 
     url : $('#AjaxMoreStatus').attr("data-url"), 
     dataType : "HTML", 
     beforeSend: function() { 
      $('.spinner').show(); 
     }, 
     complete: function() { 
      $('.spinner').hide(); 
     }, 
     success : function (data) { 
      $('#AjaxMoreStatus').append(data); 
     } 
    }); 
    } 
} 

//registering callback function to debouncing logic 
$(window).scroll(function() { 
    debounce(callback, 250); 
} 

Теперь с помощью debouncing логики, а не только вы можете решить текущие проблемы, но и вы можете перестать беспокоиться о том, когда пользователь будет остановить прокрутку страницы так что вы можете назвать свою целевую функцию, так как она может продолжаться 500 миллисекунды или даже до 1 сек.

Приведенный выше код является общим, поэтому вам не нужно делать какие-либо предположения о взаимодействии с пользователем на вашем скрипте.

Ref: https://davidwalsh.name/javascript-debounce-function

Смежные вопросы