基于原生js的图片延迟加载

当页面图片比较多的时候,我们通常会做一个延迟加载,避免页面打开时一下子的请求数太多,加载过慢影响用户体验。

如果项目用了jquery框架,则可以直接用 jquery.lazyload.可在jquery官网下载到。

如果项目是基于原生js的,可以参考以下:

<!doctype html>

<html lang="en">

<head>

    <meta charset="UTF-8">

    <title>lazyload class</title>

    <style>

    img{width:auto; height:300px;}

    </style>

</head>

<body>

    <h1>测试图片延迟加载效果</h1>

    <p><img data-url="images/p1.jpg" src="images/grey.gif" alt="p1"></p>

    <p><img data-url="images/p2.jpg" src="images/grey.gif" alt="p2"></p>

    <p><img data-url="images/p3.jpg" src="images/grey.gif" alt="p3"></p>

    <p><img data-url="images/p4.jpg" src="images/grey.gif" alt="p4"></p>

    <p><img data-url="images/p5.jpg" src="images/grey.gif" alt="p5"></p>

    <p><img data-url="images/p6.jpg" src="images/grey.gif" alt="p6"></p>

    <script>

        var API = {

            on : function(ele, ev, handler){

                ele.addEventListener ? ele.addEventListener(ev, handler) : ele.attachEvent('on' + ev, handler);

                return ele;

            },

            bind: function(obj, handler){

                return function(){ handler.apply(obj,arguments); }

            },

            pageX: function(ele){

                var left = 0;

                do{

                    left += ele.offsetLeft;

                }while(ele.offsetParent && (ele = ele.offsetParent).className.toLowerCase() !=='body');

                return left;

            },

            pageY: function(ele){

                var top = 0;

                do{

                    top += ele.offsetTop;

                }while(ele.offsetParent && (ele = ele.offsetParent).className.toLowerCase() !=='body');

                return top;

            },

            hasClass: function(ele,cls){

                return new RegExp('^|\\s' + cls + '\\s|$').test(ele.className);

            },

            attr: function(ele,attr,val){

                if(val===undefined){

                    return ele.getAttribute(attr);

                }else{

                    return ele.setAttribute(attr, val);

                }

            }

        };



    function Lazyload(id, diff, attr){

      this.container = typeof id === 'string' ? document.getElementById(id) : document.body;

      this.imgs = [].slice.call(this.container.getElementsByTagName('img'));

      this.diff = diff || 0;

      this.attr = attr || "data-url";

      this.load();//尝试加载正处在视窗中的图片

      this.spyScroll();

    }



    Lazyload.prototype = {

      constructor: Lazyload,

      spyScroll: function(){

          API.on(window, 'scroll', API.bind(this, this.load) );

      },

      load: function(){

          if(!this.imgs.length) return; //all image loaded

          var pos,url,imgs = this.imgs.slice();//copy the array

          var c=0;

          for(var i = 0, len = imgs.length; i < len; i++){

              pos = this.pos2viewport(imgs[i]); 

              if(pos === 'above' || pos === 'in'){ //console.log(imgs[i],pos,i,'      imgs.length=',len);

                  url = API.attr(imgs[i], this.attr); 

                  API.attr(imgs[i], 'src',url);

                  API.on(imgs[i], 'load', function(){

                      this.style.width='auto';//图片加载后 采用图片真实尺寸

                      this.style.height = 'auto';

                  });

                  this.imgs.splice(i-c,1); c++;//保持两数组元素的对应关系

              }

          }

        },

      pos2viewport:function(img){//img's position relative to viewport. above, in , below

        var imgScrollTop = API.pageY(img), diff = this.diff,

            rangeT = imgScrollTop - diff,

            rangeB = imgScrollTop + img.clientHeight + diff,

            viewportT = document.documentElement.scrollTop || document.body.scrollTop,

            viewportB = viewportT + document.documentElement.clientHeight;

        var pos = '';

        viewportT >= rangeB && (pos = 'above');

        viewportB <= rangeT && (pos = 'below');

        !pos && (pos = 'in');

        return pos;

      }

    };



    var lazy =  new Lazyload(document.body, 50);

    </script>

</body>

</html>

 

你可能感兴趣的:(延迟加载)