Mike
Mike

Reputation: 8877

How can I implement a dynamic class in my view?

I'm using Ionic 2, which sits on top of Angular 2. I would like to have a class added to my ion-header element. This is to allow me to have the header have a transparent background initially, but a solid background on scroll.

I am setting a variable in my Typescript file, and updating that variable when the user scrolls.

I need to set the class based on the variable in my Typescript variable. I have done this elsewhere in my app with [ngClass]="{showBack: navBack}" but this doesn't seem to work on this page.

Typescript:

import { Component, ViewChild } from '@angular/core';
import { Content } from 'ionic-angular';

@Component({
  selector: 'page-class',
  templateUrl: 'class.html'
})
export class ClassPage {
  @ViewChild(Content)
  content: Content;
  navBack: boolean = false;

  constructor(...){}

  ngAfterViewInit() {
    this.content.ionScroll.subscribe((event) => {
      if(event.scrollTop == 0) {
        this.navBack = false;
      } else {
        this.navBack = true;
      }
    });
  }

}

HTML:

<ion-header [ngClass]="{showBack: navBack}">
  <ion-navbar>
    <ion-title>Test</ion-title>
  </ion-navbar>
</ion-header>

<ion-content>
  <p style="height: 300px">Long page of content here.</p>
  <p style="height: 300px">Long page of content here.</p>
  <p style="height: 300px">Long page of content here.</p>
</ion-content>

I would expect to see a showBack CSS class on my ion-header which appears on scroll, however it never appears, regardless of the value of event.scrollTop.

I have done some debugging with console.logs on the ngAfterViewInit function, and I can confirm the variable is being changed correctly, but the class does not update.

Upvotes: 3

Views: 622

Answers (2)

Swapnil Patwa
Swapnil Patwa

Reputation: 4099

In order for something to trigger change detection it needs to be executed within Angular’s zone.

import { Component, ViewChild, NgZone } from '@angular/core';
import { Content } from 'ionic-angular';

@Component({
  selector: 'page-class',
  templateUrl: 'class.html'
})
export class ClassPage {
  @ViewChild(Content)
  content: Content;
  navBack: boolean = false;

  constructor(private ngZone: NgZone){}

  ngAfterViewInit() {
    this.content.ionScroll.subscribe((event) => {
      this.ngZone.run(() => {
          if(event.scrollTop == 0) {
            this.navBack = false;
          } else {
            this.navBack = true;
          }
    });
   });
}

}

Upvotes: 1

Dean Chalk
Dean Chalk

Reputation: 20481

Shouldn't it be:

[ngClass]="{'showBack': navBack}"

(you're missing single quotes)

Upvotes: 2

Related Questions