Search code examples
cssangularng-classangular-ng-class

ngClass does not switch value when using object in component


When I use the following code to switch the class everything works fine

<p [ngClass]="idPresent ? 'alert alert-success' : 'alert alert-danger'">
  Working
</p>

On changing the value of IdPresent in the component, I can see the appropriate class being applied,

but when I use an object in the component for the same purpose it only works if idPresent is false. When I set the idPresent to true, the following code does not apply the appropriate class.

<p [ngClass]="idValueClass">
   Not working
</p>
public idPresent = false;
 
public idValueClass = {
  "alert alert-success" : this.idPresent,
  "alert alert-danger"  : !this.idPresent
};

Can someone help me figure out what am I doing wrong?

Update:

I am changing the value of idPresent after receiving response from REST API call

 ngOnInit(): void {
 this.http.get('http://localhost:8083/v1/uniqueid', {
  headers: {'Authorization':'Basic dXNlcjpwYXNzd29yZA=='}
 })
 .subscribe(response => {
    if(response) {
      console.log(response)
       this.serverId = response;
       this.idPresent = true;
    } else {
       this.idPresent = false;
    }
    console.log("idPresent : " + this.idPresent)
 })

}

After receiving response from server, I can see updated value in console.


Solution

  • To complementary @Yong Shun, in Angular 16 and 17 we can use signal

    We can define:

      public idPresent = signal(false);
    
      public idValueClass = computed(() => ({
        alert: true,
        'alert-success': this.idPresent(),
        'alert-danger': !this.idPresent(),
      }));
    
      onClick() {
        this.idPresent.update(value => !value);
      }
    

    Be carefull, the .html we need reemplace idPresent by idPresent() and idValueClass by idValueClass()

      <p [ngClass]="idValueClass()">
        Not working
      </p>
      Current idPresent: {{ idPresent() }}
    

    A stackblitz full stolen from the Yong Shun stackblitz.

    NOTE: See that in the stackblitz I use changeDetection:ChangeDetectionStrategy.OnPush, but, when a signal is update, Angular update the entire view