正在加载中

最后更新于 2019年05月04日

现在给网站做了一个load的加载效果,但是目前流行的应该是Skeleton Screen 骨架屏,这个原本是在苹果端app里制作的,然后有人自己移植到web端,常见h5架构页面,如饿了么、知乎、facebook、酷安,都有应用,那么我就很好奇了,到底是怎么做的,于是百度了一下。

了解Skeleton Screen 骨架屏

解释有下:

简单来说,骨架屏就是在页面内容未加载完成的时候,先使用一些图形进行占位,待内容加载完成之后再把它替换掉。

通过 puppeteer 在服务端操控 headless Chrome 打开开发中的需要生成骨架屏的页面,在等待页面加载,渲染完成之后,在保留页面布局样式的前提下,通过对页面中元素进行删减或增添,对已有元素通过层叠样 式进行覆盖,这样达到在不改变页面布局下,隐藏图片和文字,通过样式覆盖,使得其展示为灰色块。然后将修改后的 HTML 和 CSS 样式提取出来,这样就是骨架屏了.

那么从上面的解释中我们可以得知,其原理就是在加载之前就要生成骨架页面,骨架页面的原理其实就是在不改变页面布局的情况下,通过修改html和css将原有的内容进行隐藏覆盖,然后等待加载完毕后再将内容替换出来。

这样一想,就很简单了,依我个人之见是这样的:网页的初始状态就是骨架结构,用户打开就是骨架状态,当页面dom加载完毕后,就开始慢慢将骨架的样式隐去,显示出内容。

如图:

代码

我的想法是这样,因为你不可能去判断到每个元素的内容是否加载完毕,即便你给每个元素添加load事件,那么资源的损耗就和实际收入完全不成正比,所以我是在load事件完成后将所有的骨架慢慢消失,本来想通过计算透明度的方式来设置骨架消失的动效,但是经过这段时间的使用这种计算方法,发现非常消耗资源,为此我采用了业界常用的class方法。

首先给需要显示骨架的元素添加一个名为vu的class,这个class本身relative,然后创建他的伪类before,通过伪类的absolute浮动到最上层,然后添加背景层将该元素的内容遮盖。

此时已经达到了我预期的效果。

css

.vu {
    position: relative;
}
.vu::before {
    content: "";
    position: absolute;
    top: 0;bottom: 0;
    left: 0;right: 0;
    height: 100%;
    background-color: #eee;
    opacity: 1;
    transition: opacity 1s;
}
.nu::before {
    opacity: 0;
    
}

js

js部分我就判断,当load事件加载完毕——获取class名为vu的元素集合,for语句循环这个数组,给每个元素添加一个Timeout延迟运行,这样就可以达到骨架一个个慢慢消失而不是集体消失,然后我们使用的时候添加的是class=nu,所以在opacity的动画还未消失前,我们不能直接删除这个vu,为此又添加了一个延迟,在1s后删除,这样刚好在动画完毕后class也删除了,这样既不影响原来的布局也不会造成混乱,非常奈斯!

window.onload = function(){
    var vu = document.getElementsByClassName('vu')
    for(var i = 0;i<vu.length;i++) {
        var son = vu[i];
        setson(son);
    }
    function setson(son) {
        setTimeout(function(){
            addClass(son,'nu');
            setTimeout(function(){
                removeClass(son,'vu');
            },1000)
        },500)
    }
    
    function addClass(element,name) {
        if(!element.className.match(new RegExp('(^|\\s)'+name+'(\\s|$)'))) {
            element.className += ' ' + name;
        }
    }
    function removeClass(element,name) {
        if(element.className.match(new RegExp('(^|\\s)'+name+'(\\s|$)'))) {
            element.className = element.className.replace(new RegExp('(^|\\s)'+name+'(\\s|$)'),' ');
        }
    }
};

效果图+在线预览:

浏览地址点击

资源下载

本人也提供资源下载,有兴趣的可以自己下载使用,当然也是为了我以后忘记了还能再看看!

蓝奏云 密码:8lc9

  • weixiao kaixin tushetou jingkong deyi fanu liezui liuhan daku ganga bishi nanguo lihai qian yiwen numu tu yi haixiu se fadai minyan hehe henkaixin huaji biyiyan kuanghan maimeng shui xiaku penqi zhangzui pen aini ye niu laji ok chigua renshi kongbu shuai xiaoxiese touxiao huaixiao jingnu chihuai kaisang xiaoku koubi zhuangbi lianhong kanbujian shafa zhijing xiangjiao dabian yaowan redjing lazhu rizhi duocang chixigua hejiu xixi xiaopen goukun xiaobuchu shenme wusuowei guancha lajing chouyan xiaochi bie zhadanzui zhadanxiao

登录