溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊(cè)×
其他方式登錄
點(diǎn)擊 登錄注冊(cè) 即表示同意《億速云用戶服務(wù)條款》

Angular中組件樣式的工作原理是什么

發(fā)布時(shí)間:2021-07-05 13:46:43 來(lái)源:億速云 閱讀:129 作者:小新 欄目:web開(kāi)發(fā)

這篇文章給大家分享的是有關(guān)Angular中組件樣式的工作原理是什么的內(nèi)容。小編覺(jué)得挺實(shí)用的,因此分享給大家做個(gè)參考,一起跟隨小編過(guò)來(lái)看看吧。

在開(kāi)發(fā) Angular 組件的過(guò)程中,我們習(xí)慣把組件的樣式寫(xiě)在對(duì)應(yīng)的 css 文件中,但是一直不了解 Angular 是怎樣做到樣式隔離的,比如在 A 組件中寫(xiě)了 h2 { color: red },這個(gè)樣式只會(huì)在 A 組件中生效,而不會(huì)影響到其他的組件。為了探究原理,就有了這篇文章,以下內(nèi)容基于 Angular CLI 10.1.1 版本創(chuàng)建。

組件樣式工作原理

探索

首先用 Angular CLI 創(chuàng)建一個(gè)新的 Angular 項(xiàng)目,刪除 app.component.html 中的所有內(nèi)容,替換成如下內(nèi)容:

<h2>App Component</h2>
<button class="red-button">Button</button>

app.component.css 中添加如下內(nèi)容:

.red-button {
  color: red;
}

運(yùn)行時(shí)有如下 html 代碼:

<app-root _nghost-ydo-c11="" ng-version="10.1.1">
  <h3 _ngcontent-ydo-c11="">App component</h3>
  <button _ngcontent-ydo-c11="" class="red-button">Button</button>
</app-root>

可以看到在在 app-root 元素上有一個(gè)名為 _nghost-ydo-c11 的屬性(property),app-root 里面的兩個(gè)元素都有一個(gè)名為 _ngcontent-ydo-c11 的屬性。

那么這些屬性是用來(lái)做什么的呢?

為了更好的理解,我們先創(chuàng)建一個(gè)獨(dú)立的組件,新建文件 blue-button.component.ts,內(nèi)容如下:

import { Component } from '@angular/core';

@Component({
  selector: 'app-blue-button',
  template: `
    <h3>Blue button component</h3>
    <button class="blue-button">Button</button>
  `,
  styles: [`
    .blue-button {
      background: blue;
    }
  `]
})
export class BlueButtonComponent {}

放到 app.component.html 中運(yùn)行后,會(huì)看到如下 html 代碼:

Angular中組件樣式的工作原理是什么

可以看到 app-blue-button 中也有一個(gè)以 _nghost-xxx 開(kāi)頭的屬性,還有一個(gè)和 app-root 中其他元素相同的屬性。而在組件里面的兩個(gè)元素都有名為 _ngcontent-yke-c11 的屬性。

由于每次運(yùn)行,Angular 生成的屬性字符串都是隨機(jī)的,所以后面的代碼如果出現(xiàn)了類(lèi)似的屬性都是按照這個(gè)截圖對(duì)應(yīng)的。

總結(jié)

通過(guò)觀察我們可以總結(jié)出:

  • 每個(gè)組件的宿主元素都會(huì)被分配一個(gè)唯一的屬性,具體取決于組件的處理順序,在例子中就是 _nghost_xxx

  • 每個(gè)組件模板中的每個(gè)元素還會(huì)被分配一個(gè)該組件特有的屬性,在例子中就是 _ngcontent_xxx

那么這些屬性是怎樣用于樣式隔離的呢?

這些屬性可以和 CSS 結(jié)合起來(lái),比如當(dāng)我們查看例子中藍(lán)色按鈕的樣式時(shí),會(huì)看到這樣的 css:

.blue-button[_ngcontent-yke-c11] {
    background: blue;
}

可以看出,Angular 通過(guò)這種方式使 blue-button 類(lèi)只能應(yīng)用于有這個(gè)屬性的元素上,而不會(huì)影響到其他組件中的元素。

知道了 Angular 對(duì)樣式隔離的行為,那么 Angular 又是如何做到這些的呢?

在應(yīng)用啟動(dòng)時(shí),Angular 將通過(guò) styles 或 styleUrls 組件屬性來(lái)查看哪些樣式與哪些組件相關(guān)聯(lián)。之后Angular 會(huì)將這些樣式和該組件中元素特有的屬性應(yīng)用到一起,將生成的 css 代碼包裹在一個(gè) style 標(biāo)簽中并放到 header 里。

Angular中組件樣式的工作原理是什么

以上就是 Angular 樣式封裝的原理。

:host, :host-context, ::ng-deep

在實(shí)際開(kāi)發(fā)中,這種機(jī)制有時(shí)候并不能完全匹配我們的需求,針對(duì)這種情況, Angular 引入了幾種特殊的選擇器。

:host

使用 :host 偽類(lèi)選擇器,用來(lái)作用于組件(宿主元素)本身。

比如,當(dāng)我們想給 app-blue-button 加個(gè)邊框時(shí),可以在這個(gè)組件的樣式中添加如下代碼:

:host {
  display: block;
  border: 1px solid red;
}

通過(guò)查看運(yùn)行時(shí)的代碼,可以看到如下代碼塊:

  <style>
    [_nghost-yke-c11] {
      display: block;
      border: 1px solid red;
    }
  </style>

:host-context

有時(shí)候,基于某些來(lái)自組件視圖外部的條件應(yīng)用樣式是很有用的。 例如,在文檔的 <body> 元素上可能有一個(gè)用于表示樣式主題 (theme) 的 CSS 類(lèi),你應(yīng)當(dāng)基于它來(lái)決定組件的樣式。

這時(shí)可以使用 :host-context() 偽類(lèi)選擇器。它也以類(lèi)似 :host() 形式使用。它在當(dāng)前組件宿主元素的祖先節(jié)點(diǎn)中查找 CSS 類(lèi), 直到文檔的根節(jié)點(diǎn)為止。在與其它選擇器組合使用時(shí),它非常有用。

在下面的例子中,會(huì)根據(jù)祖先元素的 CSS 類(lèi)是 blue-theme 還是 red-theme 來(lái)決定哪個(gè) CSS 會(huì)生效。

import { Component } from '@angular/core';

@Component({
  selector: 'app-btn-theme',
  template: `
    <button class="btn-theme">Button</button>
  `,
  styles: [`
    :host-context(.blue-theme) .btn-theme {
      background: blue;
    }
    :host-context(.red-theme) .btn-theme {
      background: red;
    }
  `]
})
export class BtnThemeComponent { }

然后在使用的地方:

<div class="blue-theme">
  <app-btn-theme></app-btn-theme>
</div>

在運(yùn)行的時(shí)候按鈕背景就是藍(lán)色的。

::ng-deep

我們經(jīng)常會(huì)使用一些第三方 UI 庫(kù),有時(shí)候我們想改變第三方組件的一些樣式,這時(shí)候可以使用 ::ng-deep,但是要注意,Angular 已經(jīng)把這個(gè)特性標(biāo)記為已廢棄了,可能在未來(lái)的版本就被完全移除掉。

:host ::ng-deep h3 {
  color: yellow;
}

通過(guò)查看運(yùn)行時(shí)的代碼:

[_nghost-yke-c12] h3 {
    color: yellow;
}

可以看到,樣式會(huì)作用在 app-root 里的所有元素上,包括 app-root 中使用的其他組件里的元素。

感謝各位的閱讀!關(guān)于“Angular中組件樣式的工作原理是什么”這篇文章就分享到這里了,希望以上內(nèi)容可以對(duì)大家有一定的幫助,讓大家可以學(xué)到更多知識(shí),如果覺(jué)得文章不錯(cuò),可以把它分享出去讓更多的人看到吧!

向AI問(wèn)一下細(xì)節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長(zhǎng)郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI