Anders Metnik
Anders Metnik

Reputation: 6247

Setting Style attributes of ionic2 component dynamically

What I'm trying to achieve:

<ion-header [style.background-color]="(style|async)?.logoBackground">
    <ion-navbar >
        <button ion-button icon-only menuToggle [style.background-color]="(style|async)?.menuButtonBackground">
            <ion-icon name="menu"></ion-icon>
        </button>
        <ion-title [style.background-color]="(style|async)?.logoBackground">
            <dynamic-logo [style]="style"></dynamic-logo>
        </ion-title>
    </ion-navbar>
</ion-header>

I have to reuse this code, over and over again.
"style" is a variable to an JSON object, I fetch dynamically which has the "style sheet for the app".

I'd lige to write it as simple as this, on other pages:

<dynamic-header [style]="style"></dynamic-header> And having a component to set these (component appended below).

Though this is not possible in ionic2, because it'll wrap the <ion-header> in the <dynamic-header> and therefor not render the page correctly.

So I'm wondering if there is an alternative to making this as a component, maybe a way of making it as a Directive, I just havn't been able to find the necessary information about @Directive..

Also tried @Directive with binding <ion-content dynamic-content [style]="style">...</>
AND
[style]="(style|async)" gives WARNING: sanitizing unsafe style value [object Object] (see http://g.co/ng/security#xss).

TS:

import { Attribute, ChangeDetectionStrategy, Component, ElementRef, Input, Renderer, ViewEncapsulation } from '@angular/core';
import { PageStyle } from "../../providers/company-service";

@Component({
  selector: 'dynamic-header',
  templateUrl: 'dynamic-header.html',
  changeDetection: ChangeDetectionStrategy.OnPush,
  encapsulation: ViewEncapsulation.None,
})
export class DynamicHeaderComponent {
  @Input() style: PageStyle;
}

HTML:

<ion-header [style.background-color]="(style|async)?.logoBackground">
    <ion-navbar >
        <button ion-button icon-only menuToggle [style.background-color]="(style|async)?.menuButtonBackground">
            <ion-icon name="menu"></ion-icon>
        </button>
        <ion-title [style.background-color]="(style|async)?.logoBackground">
            <dynamic-logo [style]="style"></dynamic-logo>
        </ion-title>
    </ion-navbar>
</ion-header>

reformed to directive

import { Directive, HostBinding, Attribute, ChangeDetectionStrategy, Component, ElementRef, Input, Renderer, ViewEncapsulation } from '@angular/core';
import { PageStyle } from "../../providers/company-service";

@Directive({
  selector: 'dynamic-content',
  /*  templateUrl: 'dynamic-content.html',
      changeDetection: ChangeDetectionStrategy.OnPush,
      encapsulation: ViewEncapsulation.None,
  */
})
export class DynamicContentComponent {
  @Input() style: PageStyle;

  @HostBinding('style.background-image')
  get getBackgroundImage() {
    if (this.style) {
      return this.style.backgroundImage;
    }
  }

  @HostBinding('style.background-repeat')
  get getBackgroundRepeat() {
    if (this.style) {
      return "no-repeat";
    }
  }

  @HostBinding('style.background-size')
  get getBackgroundSize() {
    if (this.style) {
      return "cover";
    }
  }

  @HostBinding('style.color')
  get getTextColor() {
    if (this.style) {
      return this.style.textColor;
    }
  }
}

Upvotes: 2

Views: 2009

Answers (1)

G&#252;nter Z&#246;chbauer
G&#252;nter Z&#246;chbauer

Reputation: 658255

From directives you can only bind single styles

export class DynamicHeaderComponent {
  @Input() style: PageStyle;

  // repeat this getter for every style property
  @HostBinding('style.background-color')
  get backgroundColor() {
    if(this.style) {
      return this.style.backgroundColor;
    }
  }
}

Upvotes: 2

Related Questions