CSS-LOADER配置詳解
前注:
文檔全文請查看 根目錄的文檔說明。
如果可以,請給本項目加【Star】和【Fork】持續關注。
有疑義請點擊這里,發【Issues】。
1、概述
對于一般的css文件,我們需要動用三個loader(是不是覺得好麻煩);
1、css-loader
:
先附上官網文檔(中文)的鏈接:css-loader文檔。
不過說實話,這個官方文檔講的很糟糕,看的人一臉懵逼。
css-loader
主要用于處理圖片路徑(其實也包括例如導入css文件的路徑),并且會將css樣式打包進js文件中(以模塊的形式打包導入);
但問題在于,他不會將這些代碼插入html中,因此還需要通過例如style-loader
來實現將打包好的css代碼插入html文件中。
2、style-loader
:
同樣先附上官網文檔(中文)的鏈接:style-loader文檔
基本用法:
用于將 css-loader
打包好的css模塊,插入到html文件中,變成一個 <style>
標簽;
3、file-loader
:
file-loader文檔
基本用法:
用于處理各種資源文件,一般是圖片,不然圖片是沒辦法被同時打包的。
2、css-loader配置詳解
先吐槽一波,中文文檔里的說明,真的是描述的一點都不清楚。
2.1、root
名稱 | 類型 | 默認值 | 描述 |
root | {String} | / | 解析 URL 的路徑,以 / 開頭的 URL 不會被轉譯 |
官方文檔里對這個解釋不夠嚴謹。
首先,假如不設置設個屬性,如果理解為,以 /
開頭的url不會被轉譯,從結果來看,也不算錯;
然而,假如設置這個屬性的話,那么就不一樣了。
在面對圖片路徑時,這個屬性有三種情況:
- 當不設置這個屬性的時候,
css-loader
不會去解析以/
開頭的圖片路徑,也不會報錯; - 當設置這個屬性的時候,即使你設置其值為默認值
/
,css-loader
也會去嘗試解析這個路徑,如果找不到對應的圖片,會報錯; - 當設置這個屬性的值為非默認值,和【2】中的行為是一樣的,
css-loader
去嘗試解析這個路徑,如果找到圖片,則正常解析,找不到,會報錯;
當設置這個屬性時,是指,當url以 /
為開頭時,到底去找哪里的文件夾作為解析以 /
為開頭的url路徑的文件;
當面對css文件路徑時,即在css文件里,通過 @import
引入css文件時,這個是不對css文件的路徑生效的(即使找不到,也不會報錯)。
示例:
文件樹:
根目錄
|-- src
| |-- app.js
| |-- src
| |-- logo.png
|
|-- static
| |-- abc.png
|
|-- webpack.config.js
那么在 webpack.config.js
里配置的時候,應該這么寫:root: __dirname + '/static/'
。
__dirname
表示根目錄的絕對路徑。假如根目錄的路徑是 D:/abc/def
,那么 __dirname
就表示 D:/abc/def
,而 __dirname + '/static/
則表示 D:/abc/def/static
這就是告訴 css-loader
,遇見 /
開頭的url路徑,你應該去 D:/abc/def/static
這個路徑下去找文件。
2.2、
名稱 | 類型 | 默認值 | 描述 |
url | {Boolean} | true | 啟用/禁用 url() 處理 |
首先,我們已知,css-loader
正常會解析css屬性里的圖片url路徑,例如 background: url('/logo.png')
里面的值。
那么,假如某圖片不在你的工程里,而是在服務器上。
而你是可以預知打包后的html文件和這個圖片的相對路徑關系,你就可以直接寫那個時候的路徑,并將url設置為false。
但是,如果設置為false,那么所有url都不會進行轉義了(也不會觸發file-loader),自然也不會報錯(即使圖片不存在)。
示例:
假如打包后,上傳到服務器的目錄為:
dist
|-- app.js
|-- logo.png
那么你如果想引用 logo.png
,那么把 url
設置為 false
之后,然后路徑這么寫就行了 background: url('./logo.png')
。
2.3、alias
名稱 | 類型 | 默認值 | 描述 |
alias | {Object} | {} | 創建別名更容易導入一些模塊 |
說實話我自己搗鼓了半天也沒徹底搞明白其原理,但是琢磨出來一些用法:
1、對圖片路徑生效
假如文件結構:
根目錄
|--static
| |-- logo.png
|-- webpack.config.js
解釋:
- 已知: 圖片放在
/static
目錄下; - 已知:不確認css文件放在哪里(因為模塊化,方便移動,所以可能更改模塊的目錄結構);
- 需求:我想要確保我的css文件必然能引用到這個圖片,即使更改模塊的文件路徑,也不影響(不需要我二次去修改);
- 行動:那么添加
css-loader
的屬性,設置如下:alias: {'@': __dirname + '/static/'}
; - 行動:在css文件里,圖片如下引用
background: url(~@/logo.png)
; - 結果:我就可以確保必然css文件必然能引用到這個圖片了;
- 注意:
@
前要加~
讓webpack
識別(~
是webpack
負責識別,認為是根目錄,而@
是css-loader
負責);
2、對 @import
引入的css文件無效;
假如文件結構:
根目錄
|--static
| |-- style.css
| |-- foo.css
|-- webpack.config.js
解釋:
- 文件目錄結構如上;
- 在
style.css
如果通過@import '~@/foo.css'
來導入; - 即使在
webpack.config.js
里這么設置alias: {'@': __dirname + '/src/style/'}
也是沒有用的;
3、解決場景:
這個可以應用的場景挺多,不過現在很多是通過webpack的別名通用配置來解決
- css文件和圖片文件分離;
- 也可以分類擺放圖片(例如@開頭的是風景類圖片,peopel開頭的是人物圖片);
- 記得在別名之前加一個波浪線~讓webpack識別,否則無法正常工作;
2.4、import
名稱 | 類型 | 默認值 | 描述 |
import | {Boolean} | true | 啟用/禁用 @import 處理 |
- 假如你通過@import導入的是某個打包后工程所在位置的css文件;
- 即該文件不在打包前的工程里(例如CDN);
- 那么這個就有用;
- 表現效果@import導進來的css沒有被打包,只是單純的引入了(該@import代碼被直接放在style標簽里);
- 你可以查看dist/index.html的style標簽來深刻了解;
這里給一個簡單的示例:
webpack打包前:
// foo.css
@import 'http://abc.com/m.css'
webpack打包后:
// html文件(假設使用了style-loader把css通過style標簽插入)
<style>
@import 'http://abc.com/m.css'
</style>
2.5、minimize
名稱 | 類型 | 默認值 | 描述 |
minimize | {Boolean|Object} | false | 啟用/禁用 壓縮 |
- 這個很好理解,原本寫css文件的時候,我們各種換行空格,這個改為true之后,換行和空格就去掉了;
- 一般開發的時候,取環境變量,當環境變量為生產環境的時候,設置為true;開發環境的時候,設置為false;
- 關于生產環境的配置,可以查看參考示例,搜索
minimize
即可;
壓縮前代碼:
* {margin: 0;border: 0;padding: 0;
}.box {border-radius: 150px;
}
壓縮后代碼:
*{margin:0;border:0;padding:0}.box{border-radius:150px}
2.6、sourceMap
名稱 | 類型 | 默認值 | 描述 |
sourceMap | {Boolean} | false | 啟用/禁用 Sourcemap |
- 在
minimize
設置為true
后,css代碼被壓縮了,那么如果我們要調試的話就很麻煩; - 當
sourceMap
設置為true
后,通過Chrome控制臺的Sources
標簽,在左邊欄上面選Sources
,可以在樹結構的(no domain)
里,查看到壓縮后和壓縮前的CSS代碼; - 即使
minimize
沒有設置為true
(不壓縮),由于css代碼被扔到了js里,因此也是無法直接查看我們寫的css代碼的; - 但是
sourceMap
設置為true后,就可以通過【2】中描述的途徑來查看我們寫的css代碼;
啟用 sourceMap
壓縮前的代碼:
啟用 sourceMap
壓縮后的代碼:
2.7、importLoaders
名稱 | 類型 | 默認值 | 描述 |
importLoaders | {Number} | {Number} | 在 css-loader 前應用的 loader 的數量 |
說實話,加不加這個,感覺沒啥區別(我還專門研究了一波postcss和autoprefixer讓他生效。
見我關于postcss的配置,為了正常運行,我在項目里webpack把這個注釋掉了,可以取消掉注釋 // importLoaders: 0 // 感覺沒什么用
如果有見解,歡迎指正
2.8、modules等
名稱 | 類型 | 默認值 | 描述 | 說明 |
modules | {Boolean} | false | 啟用/禁用 CSS 模塊 | 1、初步理解:這個相當于把css視為模塊。例如我有一個css文件 foo.css ,然后里面有一個類 .bar,我可以在js文件里通過 import foo from './foo.css'導入這個css文件; 2、在打包后,foo.css里的類 .bar 會變成具有唯一性的一個字符串(舉個例子假設他變成了abcdefg); 3、假如我在html里使用的是class='bar',那么顯然是無法正常生效的(bar被轉為了abcdefg); 4、那么我可以使用變量foo.bar(在js這里,這是一個變量),賦給原本使用class='bar'的這個DOM節點; 5、由于是變量,所以他的值事實上已經被css-loader轉為了abcdefg,可以正常運行了; 6、推薦阮一峰的博客CSS Modules 用法教程 |
camelCase | {Boolean|String} | false | 以駝峰化式命名導出類名 | 1、這個需要結合modules來看,在modules設置為true時,我們可以通過變量名來獲取更名后的css類名; 2、但我們寫css類名的時候,一般是例如foo-bar這種寫法,在js里顯然不合適; 3、因此把這個啟用為true,我們就可以使用fooBar這種駝峰式寫法了,方便js引用; |
localIdentName | {String} | [hash:base64] | 配置生成的標識符(ident) | 1、這個也是跟modules相關的,用于對原本混算復雜不具有可讀性的類名,進行重命名; 2、我覺得這個文章講這個比較好,你真的知道 css-loader 怎么用嗎?,搜索關鍵詞:localIdentName |
這三個是一起使用的的,見表格內容吧。
3、項目地址
https://github.com/qq20004604/webpack-study/tree/master/5%E3%80%81Loader/css_loader ,請 Star 和 fork 到本地后,注意相關配置。