图片渐进式加载

图片渐进式加载

渐进式加载是指图片在加载过程中由模糊到清晰的一个加载过程,需要两张图片实现,一张体积比较小,一张为原图,体积比较小的图片会先加载成功,然后对其进行模糊化处理,直到原图加载成功后,用原图替代体积较小的图。

图片渐进式加载_第1张图片

css filter模糊处理:

  • html
<div class="placeholder" data-large="https://pic2.zhimg.com/50/v2-c5174d0b98facea9584e7766862decdd_400x224.jpg">
    <img src="https://pic2.zhimg.com/50/v2-c5174d0b98facea9584e7766862decdd_60w.jpg" class="img-small">
    <div style="padding-bottom: 66.6%;">div>
div>
  • css
.placeholder {
    width: 200px;
    background-color: #f6f6f6;
    background-size: cover;
    background-repeat: no-repeat;
    position: relative;
    overflow: hidden;
}

.placeholder img {
    position: absolute;
    opacity: 0;
    top: 0;
    left: 0;
    width: 100%;
    transition: opacity 1s linear;
}

.placeholder img.loaded {
    opacity: 1;
}

.img-small {
    filter: blur(50px);
    /* this is needed so Safari keeps sharp edges */
    transform: scale(1);
}
  • js
window.onload = function () {

    var placeholder = document.querySelector('.placeholder'),
    small = placeholder.querySelector('.img-small')

    // 1: load small image and show it
    var img = new Image();
    img.src = small.src;
    img.onload = function () {
        small.classList.add('loaded');
    };

    // 2: load large image
    var imgLarge = new Image();
    imgLarge.src = placeholder.dataset.large;
    imgLarge.onload = function () {
        // small.classList.remove('loaded');
        imgLarge.classList.add('loaded');
    };
    placeholder.appendChild(imgLarge);
}

canvas模糊处理:

  • html
<div class="figure">
    <div class="aspect-ratio-fill">div>
    <img id="smallImg" class="small-img" crossorigin="anonymous" src="https://pic2.zhimg.com/50/v2-c5174d0b98facea9584e7766862decdd_60w.jpg"
        alt="">
    <canvas id="canvas" class="canvas">canvas>
    <img class="big-img" data-src="https://pic2.zhimg.com/50/v2-c5174d0b98facea9584e7766862decdd_400x224.jpg">
div>
  • css
.figure {
    position: relative;
    width: 200px;
    overflow: hidden;
}

.aspect-ratio-fill {
    padding-bottom: 66.67%;
}

.figure img,
.figure canvas {
    position: absolute;
    top: 0;
    left: 0;
    width: 100% !important;
    height: 100% !important;
    opacity: 1;
    transition: opacity 2s linear;
}

.canvas.loaded {
    opacity: 0;
}

.small-img {
    display: none;
}
  • js
let smallImg = document.querySelector('.small-img'),
    canvas = document.querySelector('.canvas'),
    bigImg = document.querySelector('.big-img');
ctx = canvas.getContext('2d');
smallImg.onload = function () {
    StackBlur.image(smallImg, canvas, 20, true);
    if (bigImg.getBoundingClientRect().top > 0 && bigImg.getBoundingClientRect().bottom < window.innerHeight) {
        bigImg.setAttribute('src', bigImg.dataset.src);
        bigImg.onload = function () {
            canvas.classList.add('loaded');
        }
    }
}
参考文献:

[1] How Medium does progressive image loading

[2] More examples of Progressive Image Loading

[3] medium.com 是如何让图片加载时从模糊到清晰的?

你可能感兴趣的:(javascript,css,html,canvas)