react lazyload

思路: 
DOM加載時,<img> 標籤裏,添加data-src路徑 = src 路徑, src路徑 = 本地默認圖片路徑,
DOM加載完成後,監聽頁面可視區域,有data-src時,就將src路徑替換成data-src路徑,進行圖片加載。

/**
* 頁面
*/
import LazyLoad from '../libs/LazyLoad';
imglazyload(htmlStr) {
let imgList = [];
const src = [];
const dataSrc = [];
const imgSrc = [];
let newHtmlStr = htmlStr;
imgList = newHtmlStr.match(/<img [^>]* src=['"]([^'"]+)[^>]*>/gi, function (match, capture) {
});
/*
匹配圖片(g表示匹配全部結果i表示區分大小寫)
const imgReg = /<img.*>/gi;
匹配src屬性
*/
const srcReg = / src=['"]?([^'"]*)['"]?/gi;
/* 匹配data-src屬性
var dataSrcReg = / data-src=['"]?([^'"]*)['"]?/gi; */
if (imgList) {
for (let i = 0; i < imgList.length; i++) {
src[i] = imgList[i].match(srcReg);
/* dataSrc[i] = imgList[i].match(dataSrcReg); */
/* dataSrc賦值src,且不隨src的改變而改變 */
dataSrc[i] = src[i].slice(0);
/* 替換src屬性 */
dataSrc[i][0] = dataSrc[i][0].replace(/src/gi, 'data-src');
/* 組裝 src data-src */
imgSrc[i] = '<img class="news_img_back"' + dataSrc[i][0];
/* 獲取圖片地址 */
newHtmlStr = newHtmlStr.replace(/<img [^>]* src=['"]?([^'"]*)['"]?/gi, imgSrc[i]);
}
      //newHtmlStr = newHtmlStr.replace(/(<img[^>]+)src=(['"]?([^'"]*)['"]?)/gi, "$1 data-src= $2"); //功能與綠色字體部分相同
        /* 進程的最後執行,即在return以後執行 */
setTimeout(LazyLoad, 0);
}

return newHtmlStr;
}

render(){
  <div dangerouslySetInnerHTML={{ __html: this.imglazyload(news.content)}} />
}
/* lazyload.js  * expects a list of: * `<img src="blank.gif" data-src="my_image.png" width="600" height="400" class="lazy">` */const $q = function (q, res) {        if (document.querySelectorAll) {            res = document.querySelectorAll(q);        } else {            const d = document, a = d.styleSheets[0] || d.createStyleSheet();            a.addRule(q, 'f:b');            for (let l = d.all, b = 0, c = [], f = l.length; b < f; b++) {                l[b].currentStyle.f && c.push(l[b]);            }            a.removeRule(0);            res = c;        }        return res;    },    addEventListener = function (evt, fn) {         window.addEventListener ? window.addEventListener(evt, fn, false)                : (window.attachEvent) ? this.attachEvent('on' + evt, fn)                : window['on' + evt] = fn;    },    _has = function (obj, key) {        return Object.prototype.hasOwnProperty.call(obj, key);    };/* src 與data-src 替換 */function loadImage(el, fn) {    const img = new Image(),        /* getAttribute() 方法返回指定屬性名的屬性值 */        src = el.getAttribute('data-src');        /* img.onload: img元素加載完後執行 */        img.onload = function () {        if (!! el.parent) {            el.parent.replaceChild(img, el);        } else {            el.src = src;        }        fn ? fn() : null;    };    img.src = src;}function elementInViewport(el) {    /* 獲取元素各邊距離頁面各邊的距離 */    const rect = el.getBoundingClientRect();    return (        rect.top >= 0        && rect.left >= 0        && rect.top <= (window.innerHeight || document.documentElement.clientHeight)    );}export default function () {    const images = [],        query = $q('[data-src]'),        processScroll = function () {            for (let i = 0; i < images.length; i++) {                if (elementInViewport(images[i])) {                    loadImage(images[i], function () {                        images.splice(i, i);                    });                }            }        };/* Array.prototype.slice.call is not callable under our lovely IE8 */    for (let i = 0; i < query.length; i++) {        images.push(query[i]);    }    processScroll();    addEventListener('scroll', processScroll);}
相關文章
相關標籤/搜索