Less用法小記

Itnd發表於2023-01-09

註釋

方法一:透過雙斜槓//的方式來進行註釋,使用此方法來進行註釋在編譯成css後,註釋在css檔案中不會進行展示。
方法二:透過斜槓加型號/** */的方式來進行註釋,註釋會留在編譯生成的css檔案中。

變數

變數的基礎使用

變數的定義是透過@變數: 變數值的形式完成的。

@width: 100px; // 這裡一定需要有分號結尾

.box {
    width: @width;
}

// 編譯結果
.box {
  width: 100px;
}

變數的擴充套件使用

less變數不僅僅能代表平常的css屬性值,有其它很多的場景下也能使用到less變數。

選擇器

@selector: h2;

@{selector} {
  color: red;
}

// 編譯結果
h2 {
  color: red;
}

URL路徑

less使用路徑來引入檔案時,需要在路徑兩邊加上單引號或者雙引號

@images: '../images';  // 這裡必須要有引號

.box {
  background-image: url('@{images}/img.jpg'); // 這裡也必須要是使用引號,並且在路徑中使用變數時需要大括號包裹變數
}

// 編譯結果
.box {
  background-image: url('../images/img.jpg')
}

在使用import關鍵字引入其它less時,變數也能發揮作用

// external.less
@color: red;

// index.less
@path: '../style/'
@import '@{path}/external.less'

.box {
  color: @color;
}

// 編譯結果
.box {
  color: red;
}

屬性名

變數值是屬性名或屬性名一部分時,在引用的時候需要帶上大括號。

@color: color;

.box {
  @{color}: green;
    background-@{color}: red;
}

// 編譯結果

.box {
  color: green;
    background-color: red;
}

混合方法

有寫過css的同學應該知道,在一些情況下,部分類選擇器有相同的css屬性設定,如果如果想要在各個類選擇器中複用這部分css屬性,那麼需要把公共的css屬性單獨拿出來,並且為每個類選擇器設定這些公共css屬性,然後再單獨為每個類選擇器設定各自的css屬性。

.box1,.box2 {
  color: #222;
  background-color: #ddd;
  border-radius: 8px;
}

.box1 {
  // box1的css屬性設定
}

.box2 {
  // box2的css屬性設定
}

less中,可以把這些步驟進行簡化,允許將一個類的屬性作為另一個類的屬性,這樣可以儲存多個屬性的設定,在其它的類中得到複用。

基礎使用方法

.box {
  color: #222;
  background-color: #ddd;
  border-radius: 8px;
}

.box1 {
  .box();
  // box1的css屬性設定
}

.box2 {
  .box;
  // box2的css屬性設定
}

// 編譯結果
.box {
  color: #222;
  background-color: #ddd;
  border-radius: 8px;
}

.box1 {
  color: #222;
  background-color: #ddd;
  border-radius: 8px;
  // box1的css屬性設定
}
.box2 {
  color: #222;
  background-color: #ddd;
  border-radius: 8px;
  // box2的css屬性設定
}

注意: 你可能會看到有些less檔案裡面的混合方式沒有在類選擇器後加上括號,例如.box,這種方式也是可行的,無需糾結使用哪種方式,自己在編寫less時保持風格統一即可。

這裡看到公共樣式也被編譯到css中去了,如果不想公共樣式被編譯到css中去,那麼只需要在類名後面加上括號。

.box() {            // 增加括號
  color: #222;
  background-color: #ddd;
  border-radius: 8px;
}

.box1 {
  .box();
  // box1的css屬性設定
}

.box2 {
  .box;
  // box2的css屬性設定
}

// 編譯結果

.box1 {
  color: #222;
  background-color: #ddd;
  border-radius: 8px;
  // box1的css屬性設定
}
.box2 {
  color: #222;
  background-color: #ddd;
  border-radius: 8px;
  // box2的css屬性設定
}

可以發現.box這個類沒有在css中出現,這樣就達到了目的。

混合引數

less中混合的用法和js中函式的用法比較相似,既可以透過傳參的方式來傳值,也可以給與引數預設值,下面給出示例程式碼

@borderWidth: 50px;
@borderStyle: dotted;
@borderColor: green;

.box(@width: 10px, @style: solid, @color: red) {
  margin-top: 20px;
  width: 200px;
  height: 200px;
  background-color: lightskyblue;
  border: @width @style @color;
}

.box1 {
  .box(); // 沒有傳入引數,那麼使用函式預設引數
}

.box2 {
  .box(@borderWidth, @borderStyle, @borderColor); 
}

.box3 {
  .box(@style: double);  // 為單個引數傳參
}

// 編譯結果

.box1 {
  margin-top: 20px;
  width: 50px;
  height: 50px;
  background-color: lightskyblue;
  border: 10px solid red;
}
.box2 {
  margin-top: 20px;
  width: 50px;
  height: 50px;
  background-color: lightskyblue;
  border: 50px dotted green;
}
.box3 {
  margin-top: 20px;
  width: 50px;
  height: 50px;
  background-color: lightskyblue;
  border: 10px double red;
}

匹配

可以利用關鍵字進行匹配,這個和函式過載的方式類似

.triangle(@_, @width: 10px, @color: lightskyblue) { // @_代表佔位符
  width: 0px;
  height: 0px;
  border: @width solid @color;
}

.triangle(top, @width: 10px, @color: lightskyblue) {
  border-color: transparent transparent @color transparent;
}

.triangle(right, @width: 10px, @color: lightskyblue) {
  border-color: transparent transparent transparent @color;
}

.triangle(bottom, @width: 10px, @color: lightskyblue) {
  border-color: @color transparent transparent transparent;
}

.triangle(left, @width: 10px, @color: lightskyblue) {
  border-color: transparent @color transparent transparent;
}

.triangle1 {
  .triangle(top);
}

.triangle2 {
  .triangle(right);
}

.triangle3 {
  .triangle(bottom);
}

.triangle4 {
  .triangle(left);
}

// 編譯結果

.triangle1 {
  width: 0px;
  height: 0px;
  border: 10px solid lightskyblue;
  border-color: transparent transparent lightskyblue transparent;
}
.triangle2 {
  width: 0px;
  height: 0px;
  border: 10px solid lightskyblue;
  border-color: transparent transparent transparent lightskyblue;
}
.triangle3 {
  width: 0px;
  height: 0px;
  border: 10px solid lightskyblue;
  border-color: lightskyblue transparent transparent transparent;
}
.triangle4 {
  width: 0px;
  height: 0px;
  border: 10px solid lightskyblue;
  border-color: transparent lightskyblue transparent transparent;
}

條件判斷

less中沒有if else這樣的判斷關鍵字,但有相應的關鍵來替代,那就是when

// when的基礎用法
.border(@width) when(@width > 200px) {
  border-color: lightskyblue;
}

// not關鍵字相當於!,用於取反
.border(@width) when not (@width > 200px) {
  border-color: green;
}

// and相當於&&
.border(@width, @height) when (@width > 200px) and (@height < 200px) {
  border-color: red;
}

// 逗號運算子相當於||
.border(@width, @height) when (@width > 200px), (@height < 200px) {
  border-color: blue;
}

數量不定的引數

less中混合方法可以像jsrest語法一樣,接收不定長度的引數

.boxShadow(@a, @rest...) {
  width: 275px;
  height: 70px;
  background-color: blue;
  box-shadow: @arguments; // @arguments接收了所有的引數
  text-shadow: @a @rest;
}

.box4 {
  margin-top: 20px;
  .boxShadow(12px, 12px, 0px, 0px, red);
}

// 編譯結果

.box4 {
  margin-top: 20px;
  width: 275px;
  height: 70px;
  background-color: blue;
  box-shadow: 12px 12px 0 0 red;
  text-shadow: 12px 12px 0 0 red;
}

名稱空間

名稱空間對通用類名進行隔離,避免類名命名衝突的問題

.container1 {
  .title {
    color: #222;
  }
}

.container2 {
  .title {
    color: #ddd;
  }
}

.box1 {
  .container1 > .title
}

.box2 {
  .container2 > .title
}

// 編譯結果

.box1 {
  color: #222;
}

.box1 {
  color: #ddd;
}

important關鍵字

important關鍵字用於增加css屬性的優先順序,用於覆蓋其它的同名css屬性,當在混合中使用important時,類中的所有css屬性都會被追加上important標記。

.base {
  color: red;
  background: green;
}

.box {
  .base() important;
}

// 編譯結果

.box {
  color: red !important;
  background: green !important;
}

迴圈

less中迴圈是透過表示式和模式匹配組合的類遞迴的方式來實現的,這裡舉個例子,使用less中的迴圈實現對文字行數限制的列舉。

.line(@i) when (@i > 0) {
  .line-@{i} {
    -webkit-line-clamp: @i;
  }
  .line(@i - 1); // 類遞迴呼叫
}

.line(3);

// 編譯結果
.line-3 {
  -webkit-line-clamp: 3;
}
.line-2 {
  -webkit-line-clamp: 2;
}
.line-1 {
  -webkit-line-clamp: 1;
}

合併

有些css屬性需要增加空格或逗號來拼接屬性值,在混合場景下,可以透過在屬性名後追加字尾完成拼接

逗號

.base-shadow {
  width: 275px;
  height: 70px;
  background-color: lightgreen;
  box-shadow+: 0px 12px 0px 0px lightyellow;
}

.mixin-shadow {
  box-shadow+: 12px 0px 0px 0px lightcoral;
}

// 編譯結果

.base-shadow {
  width: 275px;
  height: 70px;
  background-color: lightgreen;
  box-shadow: 0px 12px 0px 0px lightyellow;
}
.mixin-shadow {
  width: 275px;
  height: 70px;
  background-color: lightgreen;
  box-shadow: 0px 12px 0px 0px lightyellow, 12px 0px 0px 0px lightcoral;
}

空格

.base-comma {
  transform+_: scale(1.5);  // +_字尾增加空格
}

.mixin-comma {
  .base-comma();
  transform+_: translate(50%); //+_字尾增加空格
}

// 編譯結果

.base-comma {
  transform: scale(1.5);
}
.mixin-comma {
  transform: scale(1.5) translate(50%);
}

轉義

透過在跳脫字元前面加上~符號,編譯器不會對~修飾的表示式進行編譯。

.box {
  color: ~'green';
}

// 編譯結果
.box {
  color: green;
}

看看antd中在是如何使用less中轉義,這裡舉一個antd modal元件的例子。

@ant-prefix: ant;
@dialog-prefix-cls: ~'@{ant-prefix}-modal'

@{dialog-prefix-cls} {
  position: fixed;
}
  
// 編譯結果
ant-modal {
  position: fixed;
}

這裡其實就是屬性值變數拼串的場景,專案字首拼上具體的元件名充當元件類名字首。
可能有同學會疑惑,幹麼非要使用轉義,直接使用變數的基礎用法不就行了嗎?那就試試看會有什麼樣的結果。

@ant-prefix: ant;
@dialog-prefix-cls: @{ant-prefix}-modal // error: variable value expected

那就換一種方式

@ant-prefix: ant;
@dialog-prefix-cls: "@{ant-prefix}-modal"

// 編譯結果
"ant-modal" {         // error: at-rule or selector expected
  z-index: inherit;
  position: fixed;
}

css對帶雙引號的選擇器是不認識的,開始報錯。

結論: 就是在使用變數拼串的時候需要使用轉義來輔助使用。

繼承

就和oop語言中的繼承有著類似的含義,可以從其它類繼承其屬性。

.base {
  color: red;
}

.box {
  &:extend(.base);
  background: green;
}

// 編譯結果
.base,
.extend-base {
  color: red;
}

.extend-base {
  background: green;
}

參考

https://www.w3cschool.cn/less/nested_directives_bubbling.html

相關文章