web-dev-qa-db-ja.com

Angular 2-ディレクティブの子HTML要素に条件付きスタイルを適用します

クリックイベントに基づいてHTML要素にクラスを適用しようとしています。これは、親コンポーネントの次のスニペットに示されているように、親コンポーネントのテンプレートから子コンポーネントのセレクターのクラスプロパティを設定するときに正常に機能します。

[class.bordered]='isSelected(item)'

これにより、そのアイテムがクリックされたときのスタイルが適切に設定されます。ただし、同じ種類のクリックイベントに基づいて子コンポーネントに内部HTML要素のクラスを設定したいので、子コンポーネントのスタイルの目的のターゲットは次のとおりです。

template: `
  <div class="This is where I really want to apply the style">  
    {{ item.val }}
  </div>
`

簡単にサポートされるこれを行う方法はありますか?または、これは悪い習慣と見なされ、この種の条件付きスタイリング状況を回避するようにコンポーネントを設計する必要がありますか?

完全なコード:

@Component({
  selector: 'parent-component',
  directives: [ChildComponent],
  template: `
    <child-component
      *ngFor='#item of items'
      [item]='item'
      (click)='clicked(item)'
      [class.bordered]='isSelected(item)'>
    </child-component>
  `
})
export class ParentComponent {
  items: Item[];
  currentItem: item;

  constructor(private i: ItemService) {
    this.items = i.items;
  }

  clicked(item: Item): void {
    this.currentItem = item;
  }

  isSelected(item: Items): boolean {
    if (!item || !this.currentItem) {
      return false;
    }
    return item.val === this.currentItem.val;
  }
}


@Component({
  selector: 'child-component',
  inputs: ['item'],
  template: `
    <div class="This is where I really want to apply the style">  
      {{ item.val }}
    </div>
  `
})
export class ChildComponent {}
7
Chris

Angular2の機能をうまく利用して、これを解決するためのより良い方法を見つけました。

具体的には、:HostおよびCSS機能を使用してトリックを行う代わりに、次を変更することで変数を子コンポーネントに渡すことができます。

[class.bordered]='isSelected(item)'

子クラスの要素に設定されている場合は、

[isBordered]='isSelected(item)'

次に、子コンポーネントのテンプレートで境界クラスを適用するdivに、次を追加します。

[ngClass]='{bordered: isBordered}'

変更された完全なコードは次のとおりです。

@Component({
  selector: 'parent-component',
  directives: [ChildComponent],
  template: `
    <child-component
      *ngFor='#item of items'
      [item]='item'
      (click)='clicked(item)'
      [isBordered]='isSelected(item)'>
    </child-component>
  `
})
export class ParentComponent {
  items: Item[];
  currentItem: item;

  constructor(private i: ItemService) {
    this.items = i.items;
  }

  clicked(item: Item): void {
    this.currentItem = item;
  }

  isSelected(item: Items): boolean {
    if (!item || !this.currentItem) {
      return false;
    }
    return item.val === this.currentItem.val;
  }
}


@Component({
  selector: 'child-component',
  inputs: ['item'],
  template: `
    <div [ngClass]='{bordered: isBordered}'>
      {{ item.val }}
    </div>
  `
})
export class ChildComponent {}
4
Chris

child-componentにスタイルを追加します

@Component({
  selector: 'child-component',
  inputs: ['item'],
  template: `
    <div class="This is where I really want to apply the style">  
      {{ item.val }}
    </div>
  `,
  styles: [`
    :Host(.bordered) > div {
    // if this selector doesn't work use instead
    // child-component.bordered > div {
      border: 3px solid red;
    }
  `],
})
export class ChildComponent {}
4

このようなものは私にとって非常にうまく機能します:

import { Component } from '@angular/core';

@Component({
  selector: 'my-app',
  styleUrls: [ './app.component.css' ],
  template: `
  <button 
    (click)='buttonClick1()' 
    [disabled] = "btnDisabled"
    [ngStyle]="{'color': (btnDisabled)? 'gray': 'black'}">
    {{btnText}}
  </button>`
})
export class AppComponent  {
  name = 'Angular';
  btnText = 'Click me';
  btnDisabled = false;
  buttonClick1() {
    this.btnDisabled = true;
    this.btnText = 'you clicked me';
    setTimeout(() => {
      this.btnText = 'click me again';
      this.btnDisabled = false
      }, 5000);
  }
}

これが実際の例です:
https://stackblitz.com/edit/example-conditional-disable-button?file=src%2Fapp%2Fapp.component.html

0
BraveNewMath