图片的预加载和懒加载 及 位置距离计算

在前端开发中,网页中图片的加载速度是影响网页流畅度的一个重要因素,提到前端性能优化中图片资源的优化,懒加载和预加载就不能不说。

预加载

实现功能:先加载图片资源,防止用户在刷网页的时候出现白屏的情况
预加载的核心要点如下:

  1. 图片等静态资源在使用之前的提前请求;
  2. 资源后续使用时可以从缓存中加载,提升用户体验;
  3. 页面展示的依赖关系维护(必需的资源加载完才可以展示页面,防止白屏等);

几个误区:

  • 预加载不是为了减少页面加载时间
  • 预加载只是提前加载除去首轮加载的图片以后要用到的图片,比如通过点击等事件才会用到的图片。

实现预加载主要有三个方法:

  1. html中img标签最初设置为display:none;或者放置div,为div加背景图,设置display:none;不需要任何js
<div class="wechart_pub" style="display: none;">
	<img src="newWeb/images/official_download_qrcode.png"/>
</div>

<div class="wechart_pub" style="display: none;"></div>
  1. 单纯的js预加载图片
<div class="hidden">  
    <script type="text/javascript">
            var images = new Array()  
            function preload() {  
                for (i = 0; i < preload.arguments.length; i++) {  
                    images[i] = new Image()  
                    images[i].src = preload.arguments[i]  
                }  
            }  
            preload(  
                "http://domain.tld/gallery/image-001.jpg",  
                "http://domain.tld/gallery/image-002.jpg",  
                "http://domain.tld/gallery/image-003.jpg"  
            )  
    </script>  
</div>
  1. 使用XMLHttpRequest对象可以更加精细的控制预加载过程,缺点是无法跨域:
    使用Ajax,比直接使用JavaScript,优越之处在于JavaScript和CSS的加载不会影响到当前页面。该方法简洁、高效。
window.onload = function() {  
    setTimeout(function() {  
        // XHR to request a JS and a CSS  
        var xhr = new XMLHttpRequest();  
        xhr.open('GET', 'http://domain.tld/preload.js');  
        xhr.send('');  
        xhr = new XMLHttpRequest();  
        xhr.open('GET', 'http://domain.tld/preload.css');  
        xhr.send('');  
        // preload image  
        new Image().src = "http://domain.tld/preload.png";  
    }, 1000);  
};
懒加载

实现功能:能够按需加载,减轻服务器前端的压力。在一些图片非常多的网站中非常有用,当图片位置进入到可视区的时候才会被加载,这样对于含有很多 图片的比较长的网页来说,可以加载的更快,并且还能节省服务器带宽,用户体验好。

懒加载的要点如下:

  1. 图片进入可视区域之后请求图片资源;
  2. 对于电商等图片较多,页面很长的业务场景很适用;
  3. 可以减少无效资源的加载;
  4. 并发加载的资源过多会阻塞js的加载,影响网站的正常使用;

懒加载也就是延迟加载。
如何实现懒加载呢?要点就是html中图片的路径(这样就只需请求一次,俗称占位图),给一个data属性,里面存放图片真实地址,只有当图片出现在浏览器的可视区域内时,才设置图片正真的路径,让图片显示出来。这就是图片懒加载。

懒加载的实现步骤?

  1. 首先,不要将图片地址放到src属性中,而是放到其它属性(data-original)中。
  2. 页面加载完成后,根据scrollTop判断图片是否在用户的视野内,如果在,则将data-original属性中的值取出存放到src属性中。
  3. 在滚动事件中重复判断图片是否进入视野,如果进入,则将data-original属性中的值取出存放到src属性中。

懒加载实现代码

//懒加载代码实现
var viewHeight = document.documentElement.clientHeight // 可视区域的高度

function lazyload () {
  // 获取所有要进行懒加载的图片
  var eles = document.querySelectorAll('img[data-original][lazyload]')
  Array.prototype.forEach.call(eles, function (item, index) {
    var rect
    if (item.dataset.original === '')
      return
    rect = item.getBoundingClientRect()
    // 图片一进入可视区,动态加载
    if (rect.bottom >= 0 && rect.top < viewHeight) {
      !function () {
        var img = new Image()
        img.src = item.dataset.original
        img.onload = function () {
          item.src = img.src
        }
        item.removeAttribute('data-original')
        item.removeAttribute('lazyload')
      }()
    }
  })
}
// 首屏要人为的调用,否则刚进入页面不显示图片
lazyload()

document.addEventListener('scroll', lazyload)

相关的插件: lazyload

补充知识
  1. 屏幕可视窗口高度
//原生方法
window.innerHeight //标准浏览器及IE9+
|| document.documentElement.clientHeight //标准浏览器及低版本IE标准模式
|| document.body.clientHeight  //低版本混杂模式
//jQuery方法
$(window).height();
  1. 浏览器窗口顶部与文档顶部之间的距离,也就是滚动条滚动的距离:
//原生方法
window.pagYoffset  //标准浏览器及IE9+
|| document.documentElement.scrollTop  //兼容ie低版本的标准模式
|| document.body.scrollTop  //兼容混杂模式;
//jQuery方法
$(document).scrollTop();
  1. 获取元素的尺寸
$(elemnt).width() = elemnt.style.width;
$(elemnt).innerWidth() = elemnt.style.width+elemnt.style.padding;
$(elemnt).outerWidth() = elemnt.offsetWidth = elemnt.style.width+elemnt.style.padding+elemnt.style.border;
$(elemnt).outerWidth(true) = elemnt.style.width+elemnt.style.padding+elemnt.style.border+elemnt.style.margin;

注意
要使用原生的style.xxx方法获取属性,这个元素必须已经有内嵌的样式,如<div style="...."></div>
如果原先是通过外部或内部样式表定义css样式,必须使用elemnt.currentStyle[attr] || getComputedStyle(elemnt)[attr]来获取样式值。

function getStyle(ele,attr){
   return ele.currentStyle?
   ele.currentStyle[attr]:getComputedStyle(ele)[attr]
}
  1. 获取元素的位置信息
//jQuery方法
$(elemnt).offset().top //单纯的元素距离文档顶的距离 (包括自身的margin、top、及其他元素的所有距离属性如border,padding等值)
$(elemnt).offset().left //单纯的元素距离文档左边缘的距离。
//返回元素相对于第一个以定位的父元素的偏移距离,注意与上面偏移距的区别;
//原生方法
element.offsetTop();//其实是距离定位父元素的相对距离(包含自身的margin、top距离)
//jQuery方法
$(elemnt).position().left = elemnt.style.left;//单纯的定位偏移left,不包含margin
$(elemnt).position().top = elemnt.style.top;
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值