“ViewEncapsulation” in Angular

By admin


ViewEncapsulation
PRODUCT

” in Angular

Ah,

ViewEncapsulation
FAC

!

It’s what keeps you asleep through the night! Or does it? 😊

Let’s refresh our knowledge about

ViewEncapsulation
FAC

.


ViewEncapsulation
FAC

.Emulated

By default, all Angular components come with something called “style encapsulation”. It means that a component “encapsulates” its own styles so they only apply to elements within its scope. Styles defined in

one
CARDINAL

component will not have an effect on the elements in another component.

Angular achieves this by adding a specific attribute to the component’s host element and applying the same attribute to all the

CSS
ORG

selectors provided via Component#styles or Component#styleUrls . (taken from

Angular
ORG

’s docs)

Considering a component to be an independent unit, this is the expected behaviour. You don’t want your components to “leak” styles that affect “outside” elements.

The above is done by setting the Component.encapsulation option to

ViewEncapsulation
FAC

.Emulated (or not setting it at all since that’s the default value).

Looking at the DevTools in the Figure

1
CARDINAL

below, you can see that the my-app component has a _

nghost-ng-<id
ORG

> attribute. The same <id> is also added to the _ngcontent-

ng-<id
ORG

> attribute present on all child elements.

Figure

1
CARDINAL

: How

ViewEncapsulation
PRODUCT

.Emulated works in Angular

Note that the <id> is auto-generated by Angular and you should not rely on it being the same every time. So don’t style elements with _ngcontent-ng-abc123 !


ViewEncapsulation
FAC

.None

View encapsulation can be turned off on a component by setting the Component.encapsulation option to

ViewEncapsulation
FAC

.None .

But beware! Turning view encapsulation off means that all of the component’s styles now apply globally. They will no longer be scoped to the component, and can therefore affect any HTML element in the application.

You can see that by inspecting the component’s elements in

DevTools
ORG

:

Figure

2
CARDINAL

: How

ViewEncapsulation
FAC

.None works in Angular

Figure

2
CARDINAL

above shows us that the _nghost-ng-<id> attribute is no longer present on the my-app component, nor on any child elements. Styles added to h1 will now “leak” from the component and affect any other h1 s on the page. Had there been another h1 on the page, even in a completely different component, the color: tomato style would be applied to it.

There are valid reasons for turning encapsulation off, e.g. styling

3rd
ORDINAL

party components, or because parts of a component are dynamically created/moved to some other part of the

DOM
ORG

, e.g. a modal that is created as a child to body . Whatever the case, beware that the styles you add to a component might have an effect on unrelated elements!

But what if you want to disable view encapsulation on a component but still keep some, or all of its styles scoped to the component?

You can achieve this by nesting the styles under the component’s selector, i.e.

my-component { h1 { color : tomato ; } }

Figure

3
CARDINAL

: Component with

ViewEncapsulation
FAC

.None with styles scoped to the component


ViewEncapsulation
FAC

.

ShadowDom
ORG

Component.encapsulation can take a

third
ORDINAL

value –

ViewEncapsulation
PRODUCT

.

ShadowDom
ORG

but so far I’ve never used it in my apps. Once set, it uses the browser’s native

Shadow DOM API
PRODUCT

to encapsulate CSS styles, … (taken from

Angular
ORG

’s docs).

It looks like this in DevTools:

Figure

4
CARDINAL

: How

ViewEncapsulation
PRODUCT

.

ShadowDom
ORG

works in Angular

I don’t have experience with

ShadowDom
ORG

, so I’ve included it only for reference. You can decide for yourself whether it makes sense to use it in your apps.

Well, that’s it! I hope you learned something new about style encapsulation in Angular.

See you in the next post 👋

Share on Twitter