Less 教學:Extend、Mixins
這篇教學會介紹 Less Extend 擴展和 Mixins 混合裡常用的功能,這兩個功能屬於比較進階的應用,通常在架構較為複雜的 Less 檔案中才會見到,只要運用得當,就能大幅精簡複雜的 CSS 程式碼。
快速導覽:
Extend 擴展
Less 的 Extend 擴展功能寫法很類似「虛擬類別」,寫法是「:extend(指定的選擇器)
」,可以將指定選擇器到樣式,擴展到其他的選擇器上,但擴展需要符合下列規則:
:extend
一定放在最後,例如a:hover:extend(.oxxo)
。- 選擇器和
:extend
之間可以有空格,例如a:hover :extend(.oxxo)
。- 單行選擇器可以多次擴展,例如
a:hover:extend(.apple):extend(.oxxo)
,但不支援&:extend(.apple)
只能擴展一次。
下方的範例會將 .apple
和 h2
的樣式擴展到其他選擇器中。
/********** Less 寫法 **********/
h2 {font-size: 30px;}
.apple {color: red;}
.oxxo:extend(.apple) {}
.banana:extend(.apple):extend(h2) {background: gray;}
/********** 轉換成 CSS **********/
h2, .banana {font-size: 30px;}
.apple, .oxxo, .banana {color: red;}
.banana {background: gray;}
如果擴展的對象沒有樣式,則後方仍然需要加上 {}
大括號,或者也可透過 &
將擴展寫在樣式內部,但需要注意使用 &
無法多次擴展,下方會呈現兩種擴展的寫法:
/********** Less 寫法 **********/
h2 {font-size: 30px;}
.apple {color: red;}
.oxxo:extend(.apple) {}
.banana:extend(.apple):extend(h2) {background: gray;}
.xoox {
&:extend(h2);
}
.coconut {
&:extend(.apple); /* 使用 & 進行多次擴展需要撰寫多次 */
&:extend(h2);
}
/********** 轉換成 CSS **********/
h2, .banana, .xoox, .coconut {font-size: 30px;}
.apple, .oxxo, .banana, .coconut {color: red;}
.banana {background: gray;}
Extend 擴展使用 all、+ 或 +_
如果指定的選擇器連結有額外的選擇器,例如虛擬元素、虛擬類別或多重選擇器,在 extend
後方加上 all
,就能將這些連結的選擇器擴展到新的選擇器中,下方範例呈現有使用 all
和沒有使用的差異。
/********** Less 寫法 **********/
.a {color: red;}
.a.a30 {font-size: 30px;}
.a div {background: gray;}
.a:hover {color: blue;}
.b:extend(.a){} /* 只會擴展 .a */
.c:extend(.a all){} /* 所有與 .a 相關的選擇器都會一並擴展 */
/********** 轉換成 CSS **********/
.a, .b, .c {color: red;}
.a.a30, .c.a30 {font-size: 30px;} /* 注意沒有 .b,因為沒有擴展 */
.a div, .c div {background: gray;} /* 注意沒有 .b,因為沒有擴展 */
.a:hover, .c:hover {color: blue;} /* 注意沒有 .b,因為沒有擴展 */
除了 all
,Extend 也可以使用 +
或 +_
符號將擴展的樣式與「前一段」合併,兩者差別在於 +
轉換出來會有逗號,+_
則沒有逗號,用空白呈現,使用時合併與被合併的選擇器後方要添加相同的符號。
/********** Less 寫法 **********/
.a {box-shadow+: inset 0 0 10px #555;}
.b {box-shadow+_: inset 0 0 10px #555;}
.apple {
.a();
box-shadow+: i0 0 20px black;
}
.oxxo {
.b();
box-shadow+_: i0 0 20px black;
}
/********** 轉換成 CSS **********/
.a {background: inset 0 0 10px #555;}
.b {background: inset 0 0 10px #555;}
.apple {background: inset 0 0 10px #555, i0 0 20px black;}
.oxxo {background: inset 0 0 10px #555 i0 0 20px black;}
Mixins 混合
Less 的 Mixins 混合用法有點類似 Less 變數,Mixins 的寫法有兩種,兩種寫法不能混用。
- 使用現有的選擇器轉,混合時可使用這個選擇器的名稱,例如
.a
或加上小括號識別a.()
。- 使用小括號產生「獨立」樣式,例如
.a()
,使用時只能使用.a()
。
下方範例呈現兩種 Less Mixins 寫法的差異:
/********** Less 寫法 **********/
/* 使用標準選擇器作為混合參考 */
.a, .c {
color: red;
font-size: 20px;
border: 1px solid #000;
}
/* 後方有 () 表示定義一組樣式,這組樣式轉換後不會出現在程式碼內 */
.b() {
color: red;
font-size: 20px;
border: 1px solid #000;
}
.apple {.a;} /* 使用 .a 混合 .a 樣式,也可以寫成 .a() */
.oxxo {.b();} /* 使用 .b() 混合 .b() 樣式 */
.coconut{.c;} /* 使用 .c 混合 .c 樣式,也可以寫成 .c() */
/********** 轉換成 CSS **********/
/* 轉換後裡面不會出現 .b */
.a, .c {
color: red;
font-size: 20px;
border: 1px solid #000;
}
.apple {
color: red;
font-size: 20px;
border: 1px solid #000;
}
.oxxo {
color: red;
font-size: 20px;
border: 1px solid #000;
}
.coconut {
color: red;
font-size: 20px;
border: 1px solid #000;
}
Mixins 的參考對象為「選擇器」,因此在混合時必須撰寫完整的選擇器名稱,不然就會混合失敗,下方範例的 .oxxo
因為沒有撰寫完整選擇器名稱,就會無法混合。
/********** Less 寫法 **********/
.a {
.aaa {
color: red;
font-size: 20px;
border: 1px solid #000;
}
}
.apple {
.a .aaa(); /* 混合成功 */
}
.oxxo {
.aaa(); /* 混合失敗!! */
}
Mixins 只混合特定樣式
在進行混合的時候,基本上都會混合「全部」樣式屬性,但有時會希望只混合特定樣式,這時可以使用 []
獨立撰寫要混合的樣式,就能單獨混合特定樣式。
/********** Less 寫法 **********/
.apple {
color: red;
font-size: 20px;
background: pink;
}
.oxxo {
color: .apple[color];
}
.banana {
color: .apple[color];
font-size: .apple[font-size];
}
/********** 轉換成 CSS **********/
.apple {
color: red;
font-size: 20px;
background: pink;
}
.oxxo {
color: red;
}
.banana {
color: red;
font-size: 20px;
}
Mixins 混合時使用 Less 變數
如果 Mixins 參考的選擇器太長,也可以將 Less 變數設定為這組選擇器,屆時直接呼叫這個變數就可以進行混合動作。
/********** Less 寫法 **********/
.a .b .c .d {
color: red;
}
@oxxo: .a .b .c .d(); /* 設定變數 */
.apple {
@oxxo(); /* 呼叫變數 */
}
/********** 轉換成 CSS **********/
.a .b .c .d {color: red;}
.apple {color: red;}
Mixins 混合時使用 !important
撰寫 CSS 有時會需要用到 !important
( 建議避免使用,參考「!important 對權重的影響」),*如果在混合時使用 !important
,則混合的所有樣式都會添加 !important
*。
/********** Less 寫法 **********/
.a {
color: red;
font-size: 20px;
border: 1px solid #000;
}
.apple {
.a!important; /* 加上!important */
}
.oxxo {
.a()!important; /* 加上!important */
}
/********** 轉換成 CSS **********/
.a {
color: red;
font-size: 20px;
border: 1px solid #000;
}
/* 混合的樣式全部都加上 !important */
.apple {
color: red !important;
font-size: 20px !important;
border: 1px solid #000 !important;
}
.oxxo {
color: red !important;
font-size: 20px !important;
border: 1px solid #000 !important;
}
Mixins 混合時使用參數
除了基本的混合功能,Less Mixins 也如同「函式」一樣支援「參數」的傳遞,使用參數可以讓簡化重複的程式,讓程式碼更為精簡,下方範例會使用 @size
參數取代樣式相同但數值不同的內容。
/********** Less 寫法 **********/
.oxxo (@size) {
font-size: @size; /* 使用參數的方式定義樣式 */
}
.apple {
.oxxo(20px);
}
.banana {
.oxxo(30px);
}
/********** 轉換成 CSS **********/
.apple {font-size: 20px;} /* 將參數換成指定數值 */
.banana {font-size: 30px;} /* 將參數換成指定數值 */
Less Mixins 裡只要使用逗號「,
」分隔參數,就能撰寫「多重參數」語法,此外,參數也如同 Less 變數一般可以設定「預設值」,如果沒有賦予新的數值就會採用預設值,下方範例會使用具有預設值的多重參數,如果沒有使用該參數,就會套用預設值。
/********** Less 寫法 **********/
.oxxo (@size: 14px, @color: red, @bg: black) {
font-size: @size;
color: @color;
background: @bg;
}
.apple {
.oxxo(@size: 30px); /* 只更換 @size,其他使用預設值 */
}
.banana {
.oxxo(@bg: blue); /* 只更換 @bg,其他使用預設值 */
}
.coconut {
.oxxo(@color: yellow, @bg: blue); /* 只更換 @color 和 @bg,其他使用預設值 */
}
/********** 轉換成 CSS **********/
.apple {
font-size: 30px;
color: red;
background: black;
}
.banana {
font-size: 14px;
color: red;
background: blue;
}
.coconut {
font-size: 14px;
color: yellow;
background: blue;
}
Mixins 混合時的特殊參數 @arguments
@arguments
是一個特殊的參數,表示「帶入所有參數」,在具有多個參數的狀況下非常好用。
/********** Less 寫法 **********/
.a(@x: 0, @y: 0, @blur: 1px, @color: #000) {
box-shadow: @arguments;
}
.apple {
.a;
}
/********** 轉換成 CSS **********/
.apple {
box-shadow: 0 0 1px #000;
}
小結
Less Extend 擴展和 Mixins 混合可以做的事情比這篇教學所介紹的還要複雜,但絕大多數情境只需要使用這些常用技巧即可,至於一些進階的功能,有時透過 JavaScript 處理或改善 HTML 架構,才是比較好的解決方式。
意見回饋
如果有任何建議或問題,可傳送「意見表單」給我,謝謝~