6 ways to dynamically style Angular components

Adam Thompson
The Startup
Published in
4 min readMay 19, 2020

Writing style that updates based on a component’s state is a really common pattern on the web. There are several ways to dynamically update your styling depending on what you want to do. Let’s look at a few.

Class and Style directives

Using ngClass

The simplest way to update the style of your component is by using ngClass. This directive can dynamically add or change the class name of an element within your component. Let's imagine we have a button element that we want to mark as primary or secondary. We can write the following:

https://carbon.now.sh/8aaG8h0XGzwBfN0qObgj

With the above code, we’re toggling the primary class on the button with the variable isPrimary. But what if we want to set the class to a specific value? We can do that with Angular too:

https://carbon.now.sh/VFKKAGMCqMgfGPcx4wo3

Here we can set the buttonClass to any string, and use that string to our button element as a class. As long as we have a valid selector in our SCSS (i.e. .secondary), this will dynamically change the styling of our button component. Read more on ngClass in the Angular docs.

Customizing with ngStyle

If we needed a little more control over the styling of the element, we could use ngStyle to apply inline styling. This isn't recommended, since it often adds unnecessary specificity to the CSS declarations, and can make them hard to override. That said we could update the button style dynamically like this:

class myComponent { buttonBgColor = ‘#0a4ace’; // … later this.buttonBgColor = ‘#c20018’ }
https://carbon.now.sh/4p8lWSKeKDlnlZMBQGBX

Host binding

Those directives are great, but what do we do if we want to update the styling of the component itself rather than an element inside? To do this we use HostBinding and the :host selector.

Host binding a class

Host binding a class is like applying the ngClass directive to our component selector itself. Just like ngClass, we can either toggle a class on/off, or set the class name to a string.

There’s a tradeoff in deciding which method to use. We can write simpler code by using toggles for each class, however this could potentially lead to class conflicts (e.g. having both ‘primary’ and ‘secondary’ classes applied). Decide based on the use case whether you want to maintain a potentially long class string, or maintain toggles to remove conflicts.

@HostBinding(‘class.primary’) OR @HostBinding(‘class’)
https://carbon.now.sh/2FSWFdIUmhqva2heiTWU
:host { &.primary { background-color: var( — primary-color); } }
https://carbon.now.sh/VZpnV7mtGGrRi9L4cBDI

Host binding inline styles

Just like ngStyle, we can apply styling directly to the host element. Again, inline styling is not a recommended way to write styles, but sometimes it's needed. To dynamically change host styles, we again use HostBinding.

@HostBinding(‘style.background-color’) bgColor: ‘#0a4ace’; // … later this.bgColor = ‘#c20018’
https://carbon.now.sh/Q7cYj1gEgUGh3Atctbop

Both host binding and ngStyles provide great ways to dynamically update styles. But what happens if Angular deems our style value unsafe, and we get this warning?:

WARNING: sanitizing unsafe style value {some value}

Bypassing security for inline-styles

The above warning is caused by a value that Angular cannot automatically sanitize to protect against XSS attacks. Some common values I’ve experienced are image urls and complex grid column/row templates.

To prevent this warning we need to tell Angular that we trust the value and allow it to bypass security.

https://carbon.now.sh/o0ZkN76RiOt04dTZ2y9w

This approach however can potentially leave you vulnerable XSS attacks, and is not recommended for most projects. We need a way to safely update dynamic styles.

Custom properties

Custom properties are a great way to update styles dynamically from an Angular component, and setting it up is simple.

First we write the basic SCSS that we want to use, and initialize a custom property.

grid-template-columns: repeat(auto-fit, minmax(var( — min-col-width), 1fr))
https://carbon.now.sh/jYPCxHi1EgLZrT5lIjeh

Next we update the custom property in our Angular component:

this.elementRef.nativeElement.style.setProperty(‘ — min-col-width’, ‘384px’) }
https://carbon.now.sh/oYpmCmjqXFiX1zBlsZDg

We can use custom properties as either a part of the value, or as the whole value, like below:

https://carbon.now.sh/gVI2VLNTdH9d2b2SSncH
https://carbon.now.sh/QvIsqOpTKeYUTNXPJjVl

So there it is, there are at least 6 ways to dynamically update a component’s style based on state in Angular. Choosing which to use depends on preference, and what result you want to achieve.

I’m a designer & developer based in New York currently at New Visions for Public Schools. I’m online, and will occasionally tweet things.

--

--

Adam Thompson
The Startup

🗽🇨🇦 | Sr. UI Engineer @ MongoDB | Formerly at New Visions for Public Schools | SYDE @ University of Waterloo