单页面应用在如今的前端页面开发是愈来愈常见了。
它的好处不少,坏处也很明显:就是首屏加载每每很慢,呈现一片空白的页面,这给用户的体验感是不好的。
可资源的加载咱们除了尽可能地优化,也没有其余很好的办法了。为了解决这个体验感的问题,骨架屏应运而生。
复制代码
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>skeleton-plugin</title>
<style></style>
</head>
<body>
<div id="root"></div>
</body>
</html>
复制代码
单页面应用其实就是一个html文件,html结构里面有一个div#root,当js加载完毕而且执行完成后,id为root的div会被整个替换掉。因此由此咱们能够想到,咱们在div#root里面写一些动画之类的html结构,在js没有加载完成的时候,让用户看到的不是一片空白,而是预先写好的骨架页面。这样的体验感是否是会好一点呢。html
首先得构建一个简单的webpack项目(这个过程不详细说了)。在根目录下新建一个skeleton-plugin.js文件。因为咱们须要在每次打包的时候都从新生成新的骨架屏的index.html文件,因此这里须要用到html-webpack-plugin插件。咱们在skeleton-plugin.js插件注入html-webpack-plugin插件的监听器,在html-webpack-plugin插件生成index.html以前作骨架屏代码的插入。前端
在此以前。咱们须要了解一下webpack得plugin编写知识。下图是截于官方的一段话:(www.webpackjs.com/contribute/… webpack
由此能够知道,咱们的骨架屏插件要有一个apply的方法,在安装插件时,会被webpack compiler 调用一次。 该apply方法传入compiler参数,该参数暴露了webpack生命周期钩子函数供开发者使用,咱们可使用它来访问 webpack 的主环境。使用方法为:compiler.hooks.钩子函数名称.tap(...)。web
//skeleton-plugin.js
//引入html-webpack-plugin插件
const HtmlWebpackPlugin = require('html-webpack-plugin');
//建立一个SkeletonPlugin类
class SkeletonPlugin {
apply (compiler) {
//咱们这里监听compilation钩子函数,目的是编译建立以后,执行咱们的SkeletonPlugin插件的主要代码
compiler.hooks.compilation.tap('SkeletonPlugin', (compilation) => {
//在html-webpack-plugin插件生成资源到output目录以前,咱们完成对骨架屏代码的插入
HtmlWebpackPlugin.getHooks(compilation).beforeEmit.tapAsync(
'SkeletonPlugin',
(htmlData, cb) => {
//咱们在这个回调中作骨架屏代码的插入
//htmlData.html是html-webpack-plugin插件的template模板解析后的字符串
//在输出index.html以前,咱们将template模板里的<div id="root"></div>替换成骨架屏代码。
htmlData.html = htmlData.html.replace(
'<div id="root"></div>',
`<div id="root">
<div style="background-color:red;height:300px;display:none;" id="default" >
我是骨架屏页面
</div>
</div>`);
//最后执行cb回调,告诉webpack,咱们的插件已经操做完成,让它继续执行其余的操做
cb(null, htmlData)
}
)
});
}
}
//导出SkeletonPlugin插件
module.exports = SkeletonPlugin;
复制代码
最后在webpack的配置文件webpack.config.js里写上如下代码:app
plugins: [
new HtmlWebpackPlugin({
//index.html模板位置,上面代码中出现的htmlData.html就是这个模板解析后的内容。
template: './public/index.html',
inject: 'body',
}),
new SkeletonPlugin(),
]
复制代码
当webpack打包成功后,dist文件夹下的index.html将变成下图所示: 函数
到这里简单的骨架屏插件就完成了。但这个插件只会在首次加载页面的时候有骨架屏效果。对于其余页面是没有效果的。post
下篇文件将介绍《多页面的骨架屏插件》的编写思路。优化
(若有错误的内容请你们多多包涵,谢谢)动画