1. 程式人生 > >Webpack打包圖片檔案-url-loader

Webpack打包圖片檔案-url-loader

一,前言

上一篇介紹了webpack使用css-loader和style-loader打包css檔案
這篇介紹Webpack打包圖片檔案,方法和css檔案相似,也是使用loader實現
之前說過Webpack只能處理js和Json格式的檔案,所以css,圖片這些不是webpack能直接處理的資源
需要使用對應的loader對其進行處理,處理為webpack可以處理的模組

二,安裝配置圖片相關loader和準備圖片

安裝url-loader和file-loader:

npm install url-loader file-loader --save-dev

安裝完成後檢視package.json檔案

{
  "name": "webpack_test",
  "version": "1.0.0",
  "devDependencies": {
    "css-loader": "^1.0.0",
    "file-loader": "^1.1.11",
    "style-loader": "^0.21.0",
    "url-loader": "^1.0.1",
    "webpack": "3.8.1"
  }
}

修改webpack.config.js,新增圖片相關loader配置

const path = require('path');

module.exports = {
    entry: './src/js/entry.js'
,//入口檔案 output: { filename: 'bundle.js', path: path.resolve(__dirname, 'dist/js/') }, module: { rules: [ { test: /\.css$/, use: [ 'style-loader', 'css-loader' ] }, { // 正則匹配所有以.png,jpg,gif結尾的檔案
test: /\.(png|jpg|gif)$/, // 使用url-loader對圖片進行處理 use: [ { loader: 'url-loader', // 將小於8K的圖片以base64的形式打包到js檔案中 options: { limit: 8192 } } ] } ] } };
注意這裡使用的是url-loader,其實只用file-loader實現對圖片檔案的處理

url-loader是物件file-loader的上層封裝,相當於file-loader的語法糖
所以,使用url-loader要配合file-loader使用,也要下載file-loader才可以

url-loader增強了一個功能,就是options-limit屬性
limit:8192 配置,將小於8K的圖片以base64的形式打包到js檔案中

三,測試webpack載入圖片

為了測試小於8K的圖片以base64的形式打包到js檔案,
選兩張圖片進行測試,一張小於8K-small一張大於8K-big:

新建src/image目錄用於儲存圖片檔案,匯入small和big兩張圖片

src/css/test.css中新增樣式,使用兩張圖片:

#div1{
    width: 200px;
    height: 200px;
    background-image: url("../image/big.jpg");
}

#div2{
    width: 200px;
    height: 200px;
    background-image: url("../image/small.jpg");
}

dist/index.html檔案中新增對像是的使用:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>
<div id="div1"></div>
<div id="div2"></div>
<script type="text/javascript" src="./js/bundle.js"></script>
</body>
</html>

完成後的專案結構如下:

目錄

執行webpack命令,重新打包輸出:

bogon:webpack Brave$ webpack
Hash: c65943ffd3fb57130ef4
Version: webpack 3.8.1
Time: 451ms
                               Asset     Size  Chunks             Chunk Names
f849f13d4a110e9651a439f5f5051aa5.jpg  8.97 kB          [emitted]  
                           bundle.js  29.8 kB       0  [emitted]  main
   [0] ./src/js/entry.js 487 bytes {0} [built]
   [1] ./src/js/second.js 141 bytes {0} [built]
   [2] ./src/data/testdata.json 44 bytes {0} [built]
   [3] ./src/css/test.css 1.08 kB {0} [built]
   [4] ./node_modules/css-loader!./src/css/test.css 522 bytes {0} [built]
   [7] ./src/image/big.jpg 82 bytes {0} [built]
   [8] ./src/image/small.jpg 7.77 kB {0} [built]
    + 4 hidden modules

輸出後的dist目錄如下:

dist

大於8K的big.jpg生成為一個圖片檔案f849f13d4a110e9651a439f5f5051aa5.jpg

小於8K的small.jpg以base64形式被打包到bundle.js中

/* 8 */
/***/ (function(module, exports) {
module.exports = "data:image/jpeg;base64,/9j/4AAQSkZJRgABAQEASABIAA..."
/***/ }),

四,使用圖片資源及問題解決

此時訪問index.html:

這裡寫圖片描述

我們發現id=div2中的圖片載入成功了,但載入big.jpg失敗了

檢視console輸出:

GET http://localhost:63342/webpack/dist/f849f13d4a110e9651a439f5f5051aa5.jpg 404 (Not Found)

問題:

webpack將big.jpg轉為dist/f849f13d4a110e9651a439f5f5051aa5.jpg
使用圖片資源時,會去訪問webpack打包生成的資原始檔,但是沒有找到

原因:

根據設定,大於8K的圖片不會打包到bundle.js中
index.html查詢資源,會從當前目錄(dist目錄)下查詢,導致找不到資源
從目錄可以看到圖片不在dist/下,而是在dist/js/目錄下

解決:

方法1:可以將index.html放到dist/js/目錄下來解決這個問題
方法2:修改webpack.config.js配置,為output新增publicPath屬性指定引用資源的路徑
    設定publicPath屬性,為index.html提供資源服務時具有強制性
    index.html尋找資源時,都會去js/下去查詢,會影響熱載入

修改後重新輸出程式碼並測試:

重新輸出

五,總結

在webpack的世界裡,一切皆為模組
webpack只能處理js和json檔案(模組),css,圖片等需要藉助轉換器loader進行處理
使用url-loader和file-loader對圖片進行處理,
可以設定將較大圖片單獨輸出檔案,較小圖片以base64形式儲存到js中,以減少網路請求