环境准备
免得配置看起来太复杂,重新创建一个image-demo项目,并对webpack作一些简单配置。
index.js:
console.log('入口模块')
index.html:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>webpack</title>
</head>
<body>
<img src="./images/flower.jpg" alt="">
</body>
</html>
webpack.config.js:
const {resolve} = require('path')
const HtmlWebpackPlugin = require('html-webpack-plugin')
module.exports = {
entry: './src/js/index.js',
output: {
path: resolve(__dirname, 'build'),
filename: 'js/build.js'
},
module: {
rules: []
},
plugins: [
new HtmlWebpackPlugin({
template: './src/index.html'
})
],
mode: 'development'
}
相应的依赖自己安装咯,到了这里应该都会安装了吧。
安装loader
webpack处理图片资源需要使用html-loader和url-loader,而url-loader又依赖file-loader,所以先安装一下。
npm i html-loader file-loader url-loader -D
说明两个loader的作用:
- url-loader:将图片资源以base64格式构建到项目中或者提取到指定目录中。
- html-loader:解析html文件中的图片标签路径,并建立依赖关系,如果没有html-loader,在html中写img标签是不会被webpack识别的,url-loader的功能也不会被触发。
配置loader
在webpack.config.js中配置html-loader和url-loader。
webpack.config.js:
const {resolve} = require('path')
const HtmlWebpackPlugin = require('html-webpack-plugin')
module.exports = {
entry: './src/js/index.js',
output: {
path: resolve(__dirname, 'build'),
filename: 'js/build.js'
},
module: {
rules: [
// 处理图片资源
{
test: /\.html$/,
loader: 'html-loader'
},
{
test: /\.(jpg|png|gif|svg)$/,
loader: 'url-loader'
}
]
},
plugins: [
new HtmlWebpackPlugin({
template: './src/index.html'
})
],
mode: 'development'
}
用webpack命令构建项目。
webpack
我们可以看到build目录中并没有图片资源。
我们用浏览器访问构建后的index.html。
发现效果是实现了,为什么呢?我们再来看看index.html的内容。
原来webpack把图片变成了base64字符串插入到img标签中。这种做法的好处是可以减少http请求的数量,请求index.html的时候,图片内容就一并响应回来了。但是如果图片体积较大,或者图片很多时,我们请求index.html的等待时间就会很长,用户体验就差。
我所用到的图片大小是71kb的,跟index.html一起响应显然是不合适,需要分开加载。
图片提取构建
假如可以设定一个阈值,当图片大小大于阈值的时候就提取出来,小于阈值时就构建成base64一起响应,这样就最好了。我们需要修改一些url-loader的配置,为了看到效果,再添加一个小一点的图片。
在index.html中也引入这张图片。
index.html:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>webpack</title>
</head>
<body>
<img src="./images/flower.jpg" alt="">
<img src="./images/user.png" alt="">
</body>
</html>
修改url-loader的配置:
const {resolve} = require('path')
const HtmlWebpackPlugin = require('html-webpack-plugin')
module.exports = {
entry: './src/js/index.js',
output: {
path: resolve(__dirname, 'build'),
filename: 'js/build.js'
},
module: {
rules: [
// 处理图片资源
{
test: /\.html$/,
loader: 'html-loader'
},
{
test: /\.(jpg|png|gif|svg)$/,
loader: 'url-loader',
options: {
// 大于8k的图片就提取出来
// 这个数值看项目具体要求,8k是一个比较合适的值了
limit: 8 * 1024,
// 图片构建后输出的目录
outputPath: 'images'
}
}
]
},
plugins: [
new HtmlWebpackPlugin({
template: './src/index.html'
})
],
mode: 'development'
}
重新构建项目。
可以看到build目录下多了一个images目录,里面只有一张图片,文件名是一个hash值。再看看index.html的变化。
构建后的index.html两个图片的路径,大图片的路径一个是指向了images目录里的那张图片,小图片的路径指向了一串base64字符串,用浏览器打开index.html。
两张图片都被渲染出来了,这样就达到我们前面提到的效果了。
现在还有一个问题,输出的图片文件名太长了,看着不爽肿么办?
哈哈,别慌,简单配置一下就行!
webpack.config.js:
const {resolve} = require('path')
const HtmlWebpackPlugin = require('html-webpack-plugin')
module.exports = {
entry: './src/js/index.js',
output: {
path: resolve(__dirname, 'build'),
filename: 'js/build.js'
},
module: {
rules: [
// 处理图片资源
{
test: /\.html$/,
loader: 'html-loader'
},
{
test: /\.(jpg|png|gif|svg)$/,
loader: 'url-loader',
options: {
limit: 8 * 1024,
outputPath: 'images',
// 设置输出的文件名规则
// 中括号是占位符
// hash:10表示文件名是随机的10位hash值
// ext表示使用原有的扩展名
name: '[hash:10].[ext]'
}
}
]
},
plugins: [
new HtmlWebpackPlugin({
template: './src/index.html'
})
],
mode: 'development'
}
重新构建…
是不是就顺眼多啦!图片资源的出来相对简单,到这里基本就完成了,喜欢的小伙伴点个赞哦。下一篇讲解怎么处理其他各种各样的资源,敬请期待!拜拜!