如果還沒用過CSS變數,那你還在猶豫什麼!學起來!

語言: CN / TW / HK

theme: fancy

持續創作,加速成長!這是我參與「掘金日新計劃 · 6 月更文挑戰」的第30天,點選檢視活動詳情

前言

變數大家應該都聽過吧,我們任何一門語言都有變數的存在。我們作為一名前端開發著,不僅僅需要寫 JS 程式碼,還需要編寫大量的 CSS 樣式程式碼。在以前,我們所認知的變數僅僅是存在於 JS 中的,CSS 中是不存在變數這一說法的,即使存在也是通過 lessscss 等手段變相的實現的 CSS 變數。

但是隨著前端的不斷完善,我們原生的 CSS 也支援變量了,如果你還不會使用 CSS 變數,那趕緊一起來學一學吧!

1.基本介紹

變數有一個很大的作用就是降低維護成本,假如我們程式碼中很多地方都要用到了同一個值,這個時候我們就可以將該值使用變數維護起來,如果以後該值改變,我們只需要更改變數值即可。

作為前端開發者,編寫大量的 CSS 樣式程式碼是不可避免的,隨著專案的增加,CSS 程式碼也會變得越來越難以維護,而且我們都知道,CSS 程式碼中有很多都是重複程式碼。

假如我們確定了專案的主題色,然後在各個 CSS 程式碼中使用該了主題色,如果後期主題色變了,那豈不是所有 CSS 程式碼都得查詢更改一遍。假如我們用變數將該主題色儲存起來,後續 CSS 程式碼中直接使用變數即可,需要更改主題色時,直接更改變數值即可。

上述的主題色場景是我們經常遇到的,這也是 CSS 變數運用的典型場景。

我們先來看看官網是如何解釋 CSS 變數的。

官網解釋:

自定義屬性(有時候也被稱作 CSS 變數或者級聯變數)是由 CSS 作者定義的,它包含的值可以在整個文件中重複使用。由自定義屬性標記設定值(比如: --main-color: black;),由 var() 函式來獲取值(比如:color: var(--main-color);

變數其實很好理解,我們需要知道的是如何宣告變數以及如何使用變數,因為在各大語言中變數的宣告和使用還有些許的不同,特別是在 CSS 程式碼中,它的宣告和使用區別較大。

CSS 變數宣告:

上面官網的解釋中提到 CSS 變數又被稱作為自定義屬性,既然是屬性,那麼我們應該很熟悉,比如 colorbackground 等等都是 CSS 屬性。那麼我們的 CSS 變數就和屬性一樣,程式碼如下:

:root { --bgColor: #fff; }

上段程式碼中我們定義了一個 bgColor 變數,需要注意的是我們需要在自定義屬性前面加上--才算是變數,這算是 CSS 變數的宣告規則。自定義屬性值#fff 就是我們的變數值。上面的:root 是一個偽類,它相當於一個全域性作用域,我們都知道變數是有作用域的概念的,宣告在:root 偽類中的變數可以在全域性 CSS 程式碼中使用。

CSS 變數使用:

聲明瞭變數,那麼只有使用它才能體現它的價值,CSS 變數的使用需要使用到一個 CSS 內建函式 var()程式碼如下:

div { background-color: var(--bgColor); }

我們只需要利用 var 函式將宣告的變數包裹起來,就可以拿到它的值了。

變數命名規則:

我們都知道變數不能是隨便命名的,比如變數名不得有關鍵詞,特殊符號等等,各個語言中變數命名也有稍許不同,比如 JS 變數中不能以數字開頭,但是我們 CSS 變數允許數字開頭,比如下方程式碼:

:root { --1: #369; } div { background-color: var(--1); }

但是,CSS 變數命名還是有自己規則的,總結如下:

  • 不能包含$,[,^,(,%等字元
  • 普通字元侷限在只要是“數字[0-9]”“字母[a-zA-Z]”“下劃線_”和“短橫線-”這些組合
  • 可以是中文,日文或者韓文
  • 無論是變數的定義和使用只能在宣告塊{}裡面
  • 變數值只能用作屬性值,不能用作屬性名,比如下方程式碼我們是不允許的:

.foo { --side: margin-top; /* 無效 */ var(--side): 20px; }

2.var函式使用

前面我們說 CSS 變數的使用要依靠 var 函式,那麼 var 函式具體怎麼使用呢?我們本章詳細介紹一下。

官方解釋:

var()函式可以代替元素中任何屬性中的值的任何部分。var()函式不能作為屬性名、選擇器或者其他除了屬性值之外的值。(這樣做通常會產生無效的語法或者一個沒有關聯到變數的值。)

官方解釋得還是很好理解的,我們可以總結出下面兩點:

  • 可以替代 CSS 中任何屬性的值得任何部分
  • 它不能作為屬性名、選擇器等等,總之只能用在屬性值部分

基本語法:

既然 var()是一個函式,那麼它就有輸入輸出值,也就是引數和返回結果。var()函式比較簡單,它只接收兩個引數,程式碼如下:

var( <custom-property-name> , <declaration-value>? )

可以看到 var()函式接收兩個引數,具體表示啥意思我們一起來看看。

引數解釋:

  • <custom-property-name>:自定義屬性名,也就是我們自定義的變數。
  • <declaration-value>:可選引數,如果我們自定義的變數值無效的話,該引數就作為回退值使用,也就是 var 函式的預設值。

簡單示例:

當我們的變數值有效時,會直接採用變數值。

```

```

輸出結果:

當我們變數值無效時,採用預設值,程式碼如下:

```

```

輸出結果:

3.變數的作用域

通常來說,變數聲明後都會有作用域的,不可能我們隨便宣告一個變數,然後整個系統都可以用吧!這樣整個系統就亂套了!我們的 CSS 變數同樣也有作用域的概念。

3.1 全域性變數

前面我們將 CSS 變數宣告在了:root 偽類中,這個時候的變數就是全域性變數,即所有 CSS 樣式程式碼中都可以使用到該變數。

程式碼如下:

``` :root { --bgColor: rgb(82, 70, 70); }

div { background-color: var(--bgColor); width: 100px; height: 100px; } ```

上段程式碼中--bgColor 就是全域性變數

3.2 區域性變數

我們也可以將變數的宣告放在某一個選擇器內部,這個時候該變數就是一個區域性變數,屬於該元素的所有子元素都可以使用到該變數。

程式碼如下:

```

小豬課堂

我在 div 外面

```

輸出結果:

我們可以看到 span 標籤無法使用到我們定義的--color 變數,因為該變數屬於 div 這個作用域,只能作用域 div 以及它的子元素。

3.3 變數優先順序

當我們有多個 CSS 變數的名稱一致時,該如何取變數的值呢?我們這裡可以簡單給個規則:

如果在多個 CSS 變數命名相同,且都能讀取到的情況下,根據 CSS 選擇器的優先順序來選擇合適的變數值。

示例程式碼如下:

```

小豬課堂

我在 div 外面
  • 我沒有選擇器
  • ```

    實現效果:

    上段程式碼中我們使用了萬用字元*給所有的字型顏色都設定為了 pink,但是最終只有 li 標籤的字型顏色為 pink,是因為 li 標籤沒有單獨設定樣式,而其它標籤都利用選擇器單獨設定了樣式,所以顏色不一樣。

    上段程式碼還需要注意的是.classp 選擇其中的--color 變數將:root 中的變數覆蓋掉了,這就和 css 樣式優先順序一個道理。

    總之大家判斷 CSS 變數優先順序的時候參考 CSS 樣式的層級規則就可以了。

    4.關於變數的拼接

    有時候我們定義的變數可能是數字,可能是字串等等,當我們使用變數的時候可能需要做一些處理,比如數字要與字串拼接等等,這個時候我們需要注意什麼呢?這裡給出一些常見的需求以及功能點供大家參考。

    變數是數值時

    當我們的變數是數值時,且使用時需要與字串拼接,這是我們需要做一些處理才可以,程式碼如下:

    ``` :root { --color: yellow; --height: 100; }

    / 2 種錯誤的寫法 / div { height: var(--height)px; height: var(--height) + 'px'; }

    / 正確的寫法 / div { height: calc(var(--height) * 1px); } ```

    變數值是字串

    如果我們的變數值本身是一個字串,那麼它是可以和其它字串拼接的,程式碼如下:

    --bar: 'hello'; --foo: var(--bar)' world'; // hello world

    變數值帶有單位時

    變數值帶有單位是比較常見的,很多小夥伴可能覺得帶有單位就應該當做字串處理,其實不是,因為 css 內部本身本身就能解析單位,我們不必再使用引號將單位包裝成字串,程式碼如下:

    ``` / 錯誤的寫法 / div { --foo: '20px'; font-size: var(--foo); / 無效 / }

    / 正確的寫法 / div { --foo: 20px; font-size: var(--foo); } ```

    5.換膚原理

    換膚是 CSS 變數實踐的一個典型場景,我們通常使用 Less 或者 SassCSS 變數結合的方式來實現換膚,我們這裡直接使用 CSS 變數來演示換膚最簡單的原理。

    程式碼如下:

    ```

    ```

    實現效果:

    上段程式碼雖然很簡單,但是它基本上解釋了換膚的原理是什麼,我們通過點選按鈕實現 div 背景色的變化。如果我們再很多元素上都使用了設定的 theme 變數,那麼更改--theme 屬性值的時候,就相當於切換了主題。

    6.相容性

    由於 css 變量出現的時候並不是那麼早,所以可能存在一些相容性問題。但是最近 IE 瀏覽器都倒閉了,我們何必還要擔心相容性問題呢。

    總結

    雖然我們 CSS 變數可以實現換膚功能,但是我們在實際專案中通常採用的是 CSS 變數與 less 或者 scss 結合方式,因為我們的專案通常是 Vue 或者 react 專案,所以我們需要合理的藉助一些工具。

    如果覺得文章太繁瑣或者沒看懂,可以觀看影片: 小豬課堂