当用户向下滚动页面时,我尝试显示一些数据,但调用的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 :(得分: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调用和计时器的顶部。
答案 1 :(得分:0)
这是一个已知问题,它通过一种名为debouncing logic
的技术解决。
什么是Debouncing逻辑:哪个返回一个函数,只要它继续被调用,就不会被触发。 该函数将在停止为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
秒
上面的代码是通用的,因此您不必对脚本上的用户交互做任何假设。