相信喜欢用 jQuery 的童鞋应该多少了解过 jquery.lazyload.js (opens new window) 这个插件,看了下源码,真是相当的牛逼!关于这个插件各个参数的作用这里就不再赘述,Google 一下有一堆的详解。分析下延迟加载的原理:
在页面的 load 没有触发之前,把所有的指定 id 的元素内的 img
放入到 imgs
中,将所有的图片的 src
值放入到一个新建的 srcattr
属性中,把 src
设置为默认的显示图片。
然后,在 document.body
的 scroll
事件触发时,循环计算 imgs
中的 img
元素位置是否正好在浏览器显示框范围内,如果是,则将 img
元素的 srcattr
属性的值赋给 src
, 这样图片就能显示出来。
下面是简单的实现:
(function($) {
// $下定义一个自己的命名空间
$.xy = $.xy || {};
$.xy.imgLazyLoad = function (options) {
// 构造最终参数(默认参数设置与自定义参数合并)
var settings = $.extend({
lazySrcName : "srcattr", // 存储 img src 的自定义属性名称
scrollStep: 200 // 滚动步长
}, options)
, imgLoadStatus = 0
, $window = $(window);
var _lazyLoad = function () {
// 要延迟加载的img数组。
var defObj = $('img[' + settings.lazySrcName + ']');
// 图片加载的范围
var pageTop = function () {
return $(window).height() + $(window).scrollTop();
};
_imgLoad(defObj, pageTop());
var scrollCount = 0;
// 绑定滚动事件。
$window.bind('scroll', function () {
// 往回移动就是负数
var moved = Math.abs($window.scrollTop() - scrollCount);
// 累计滚动达到一定的值再去加载图片
if (moved >= settings.scrollStep) {
_imgLoad(defObj, pageTop());
if (imgLoadStatus == 1) {
scrollCount += settings.scrollStep;
imgLoadStatus = 0;
}
}
});
},
_imgLoad = function (defObj, pageTop) {
// 防止页面有新的图片元素
defObj = $('img[' + settings.lazySrcName + ']');
defObj.each(function () {
var srcattr = $(this).attr(settings.lazySrcName);
if (srcattr) {
// var imgTop = _getPosition($(this)[0]).y;
var imgTop = $(this).offset().top;
// 如果当前图片 的 top 值 在最大加载范围内。
if (
imgTop <= pageTop
// 如果当前图片的底边位置值大于滚动条滚动的距离
&& (imgTop + $(this).height()) >= $window.scrollTop()
) {
// 将 srcattr 的值载入 src,并且移除 srcattr 属性
$(this).attr("src", srcattr).removeAttr(settings.lazySrcName);
}
}
});
imgLoadStatus = 1;
};
_lazyLoad();
}
})(jQuery);