CSS Modules 與 scoped 的不同

What ?

css 的做用域表現。css

Css modules

是一個CSS文件,其中全部類名和動畫名稱默認爲局部做用域。
使用JS編譯原生的CSS文件,使其具有模塊化的能力,該文件須要import使用。

Scoped

在vue文件中的style標籤上,有一個特殊的屬性:scoped。
此樣式僅適用於當前組件元素,從而使組件之間的樣式不互相污染。

How ?

Css modules

實現原理html

經過給樣式名加hash字符串後綴的方式,實現特定做用域語境中的樣式編譯後的樣式在全局惟一。vue

具體效果demowebpack

// webpack.config.js
{
  test: /\.css$/,
  loader: 'style!css-loader?modules&importLoaders=1&localIdentName=[name]__[local]___[hash:base64:5]' 
}
編譯前 - vue 環境
<template>
  <div :class="$style.green">demo demo</div>
</template>

<style module>
.green {
 color: green;
}
</style>

編譯後 - vue 環境
<div class="green_3UI7s9iz">demo demo</div>

.green_3UI7s9iz {
 color: green;
}

因而可知git

  1. css module直接替換了類名,排除了用戶設置類名影響組件樣式的可能性。優勢就是沒必要再擔憂命名約定。
  2. $style.green 是個變量,便可在js中引用,引用方式爲:this.$style.green。
  3. modules 即爲啓用,localIdentName 是設置生成樣式的命名規則。

應用場景github

只應用於某個組件,其餘組件不適用。web

⚠️ 注意點less

  • 在處理動畫animation的關鍵幀keyframes,動畫名稱必須先寫:
    • 好比,animation: deni .5s,能正常編譯; animation: .5s deni, 則編譯異常
  • css modules生效方式:
    • 須要css-loader配置才能生效。
    • 若使用的是style-loader,則需配置更換爲vue-style-loader纔可生效。

css modules如何解決權重問題?dom

容許經過重命名或命名空間來封裝樣式規則,減小對選擇器的約束,從而達到不須要特定方法就可舒服的使用類名。ide

當樣式規則耦合到每一個組件時,當再也不使用組件時,樣式也會被移除。

Scoped

實現原理

vue經過在DOM結構以及css樣式上加惟一不重複的標記,以保證惟一,達到樣式私有化模塊化的目的。

具體效果demo

// 編譯前 demo.vue
<template>
  <div class="demo-c">hello world!</div>
</template>

<style lang="less" scoped>
  .demo-c {
    width: 100%;
    height: 100px;
    background-color: green;
    color: #fff;
  }
</style>
// 編譯後-dom
<div data-v-48baf84c="" class="demo-c">hello world!</div>
// 編譯後-css
.demo-c[data-v-48baf84c] {
  width: 100%;
  height: 1.333333rem;
  background-color: green;
  color: #fff;
}

應用場景

scoped css能夠直接在能跑起來的vue項目中使用,且對應的樣式只對該組件有效,不被其餘組件污染。

⚠️ 注意點

「權重加劇」的意思: 若是咱們要去修改這個樣式,須要更高的權重去覆蓋其樣式。

  • 因爲css樣式優先級的特性,scoped處理會形成每一個樣式的權重加劇了。
  • 若組件內部包含有子組件,只會給子組件的最外層標籤加上當前組件的data屬性:
    • 通常父組件若是加了scoped,會比已設置過本身樣式的子組件內除最外層標籤的內層標籤的權重低,因此不會影響他們的樣式。
  • scoped會使標籤選擇器渲染變慢更多倍。
  • 若用戶再定義了相同的類名,也有可能會影響到組件的樣式。
  • 具備scoped屬性的樣式只會應用到當前元素和其子元素。Inline樣式仍然比scoped樣式優先級高,因此,最好避免使用inline樣式。

Why ?

目的

  • css 模塊化
  • css 私有化:不被污染
  • css 複用性
  • 解決CSS中的全局做用域問題

總結

實現同一目的,比較它們的優缺點,css modules 配置並不麻煩且實現的總體效果更優於scoped css,在此我的更推薦使用css modules。

參考資料

相關文章
相關標籤/搜索