web-dev-qa-db-fra.com

Appliquer une directive sous condition

J'utilise le matériau 2 pour ajouter md-raised-button.

Je souhaite appliquer cette directive uniquement si certaines conditions sont remplies.

Par exemple: 

<button md-raised-button="true"></button>

Autre exemple: J'ai créé une forme réactive dynamique de base dans plunker . J'utilise la directive formArrayName de la forme réactive pour un tableau de contrôles . Je souhaite appliquer la directive formArrayName uniquement si la condition spécifique devient vraie. sinon, n'ajoutez pas la directive formArrayName. J'ai beaucoup essayé, mais je n'ai trouvé aucune solution. 

Voici le lien de plunker: https://plnkr.co/edit/oPZ7PyBSf8jjYa2KVh4J?p=preview

J'apprécierais vraiment toute contribution. 

Merci d'avance!

43
user2899728

Je ne sais pas si vous pouvez appliquer des directives basées sur une condition, mais une solution de contournement contournerait aurait des boutons 2 et les afficherait en fonction d'une condition.

<button *ngIf="!condition"></button>
<button *ngIf="condition" md-raised-button></button> 

Edit: peut-être ceci sera utile.

24
LLL

Vous pouvez utiliser la méthode ci-dessous:

<button [attr.md-raised-button]="condition ? '' : null"></button>

Appliqué la même chose à votre plunker: fork

Mettre à jour:

Comment condition ? '' : null fonctionne comme la valeur:

Lorsque c'est la chaîne vide (''), il devient attr.md-raised-button="", quand sa null l'attribut n'existera pas.

Mise à jour: plunker update: fork (problèmes de version résolus, veuillez noter que la question était à l'origine basée sur la forme angulaire 4)

38
Aldracor

Cela peut arriver tard, mais c'est une méthode viable et élégante d'application conditionnelle d'une directive.

Dans la classe de directive, créez la variable d'entrée:

@Input('myDirective') options: any;

Lors de l'application de la directive, définissez la propriété apply de la variable d'entrée:

<div [myDirective] = {apply: someCondition}></div>

Dans la méthode de la directive, recherchez la variable this.options.apply et appliquez la logique de la directive en fonction de la condition:

ngAfterViewInit(): void {
    if (!this.options.apply) {
        return;
    }

    // directive logic
}
9
Tiha

Comme d'autres l'ont également déclaré, directives ne peut pas être appliqué de manière dynamique.

Cependant, si vous souhaitez simplement basculer le style de md-button de flat à raised, alors ceci

<button md-button [class.mat-raised-button]="isRaised">Toggle Raised Button</button>

ferait l'affaire. Plunker

7
Ankit Singh

Comme déjà noté, cela ne semble pas être possible. ng-template peut être utilisé pour éviter au moins certaines duplications. Cela vous permet d'extraire le contenu de l'élément affecté par la branche ngIf.

Si vous voulez par exemple créer un composant de menu hiérarchique en utilisant un matériau angulaire:

<!-- Button contents -->
<ng-template #contentTemplate>
    <mat-icon *ngIf="item.icon != null">{{ item.icon }}</mat-icon>
    {{ item.label }}
</ng-template>

<!-- Leaf button -->
<button *ngIf="item.children == null" mat-menu-item
    (click)="executeCommand()"
    [disabled]="enabled == false">
    <ng-container *ngTemplateOutlet="contentTemplate"></ng-container>
</button>
<!-- Node button -->
<ng-container *ngIf="item.children != null">
    <button mat-menu-item
        [matMenuTriggerFor]="subMenu">
        <ng-container *ngTemplateOutlet="contentTemplate"></ng-container>
    </button>

    <mat-menu #subMenu="matMenu">
        <menu-item *ngFor="let child of item.children" [item]="child"></menu-item>
    </mat-menu>
</ng-container>

Ici, la directive appliquée de manière conditionnelle est matMenuTriggerFor, qui ne devrait être appliquée qu'aux éléments de menu avec des enfants. Le contenu du bouton est inséré aux deux endroits via ngTemplateOutlet.

6
H.B.

Actuellement, il existe NO une manière d'appliquer de manière conditionnelle une directive à un composant. Elle n'est pas prise en charge. Les composants que vous avez créés peuvent être ajoutés ou supprimés de manière conditionnelle. 

Il existe déjà un problème créé pour la même chose avec angular2, il devrait donc en être de même avec angular4 aswell.

Sinon, vous pouvez aller pour l'option avec ng-if

<button ngIf="!condition"></button>
<button ngIf="condition" md-raised-button></button> 
3
Sajeetharan

Je ne pouvais pas trouver une solution Nice existante, j'ai donc construit ma propre directive.

import { Directive, ElementRef, Input } from '@angular/core';

@Directive({
  selector: '[dynamic-attr]'
})
export class DynamicAttrDirective {
  @Input('dynamic-attr') attr: string;
  private _el: ElementRef;

  constructor(el: ElementRef) {
    this._el = el;
  }

  ngOnInit() {
    if (this.attr === '') return null;
    const node = document.createAttribute(this.attr);
    this._el.nativeElement.setAttributeNode(node);
  }
}

Puis votre html:

<div dynamic-attr="{{hasMargin: 'margin-left' ? ''}}"></div>

2
Cappi10

oui c'est possible.

page html avec directive appActiveAhover :)

  <li routerLinkActive="active" #link1="routerLinkActive">
        <a [appActiveAhover]='link1.isActive?false:true' routerLink="administration" [ngStyle]="{'background':link1.isActive?domaindata.get_color3():none}">
          <i class="fa fa-users fa-lg" aria-hidden="true"></i> Administration</a>
      </li>
      <li  routerLinkActive="active" #link2="routerLinkActive">
        <a [appActiveAhover]='link2.isActive?false:true' routerLink="verkaufsburo" [ngStyle]="{'background':link2.isActive?domaindata.get_color3():none,'color':link2.isActive?color2:none}">
          <i class="fa fa-truck fa-lg" aria-hidden="true"></i> Verkaufsbüro</a>
      </li>
      <li  routerLinkActive="active" #link3="routerLinkActive">
        <a [appActiveAhover]='link3.isActive?false:true' routerLink="preisrechner" [ngStyle]="{'background':link3.isActive?domaindata.get_color3():none}">
          <i class="fa fa-calculator fa-lg" aria-hidden="true" *ngIf="routerLinkActive"></i> Preisrechner</a>
      </li>

directif

@Directive({
  selector: '[appActiveAhover]'
})
export class ActiveAhoverDirective implements OnInit {
  @Input() appActiveAhover:boolean;
  constructor(public el: ElementRef, public renderer: Renderer, public domaindata: DomainnameDataService) {
}

  ngOnInit() {
  }

  @HostListener('mouseover') onMouseOver() {
    if(this.appActiveAhover){
      this.renderer.setElementStyle(this.el.nativeElement, 'color', this.domaindata.domaindata.color2);
    }
  }

  @HostListener('mouseout') onMouseOut() {
    if(this.appActiveAhover){
      this.renderer.setElementStyle(this.el.nativeElement, 'color', 'white');
    }
  }

}
2

Au 18 janvier 2019, C’est ainsi que j’ai ajouté une directive conditionnelle dans Angular 5 et plus. Je devais changer la couleur du composant <app-nav> en fonction de darkMode. Si la page était en mode sombre ou non.

Cela a fonctionné pour moi:

<app-nav [color]="darkMode ? 'orange':'green'"></app-nav>

J'espère que ça aidera quelqu'un.

0
Sandra israel

J'ai une autre idée de ce que vous pourriez faire.

Vous pouvez stocker le code HTML que vous souhaitez remplacer dans une variable sous forme de chaîne, puis ajouter/supprimer la directive à votre guise, à l'aide de la méthode bypassSecurityTrustHtml de DomSanitizer .

Je ne débouche pas sur une solution propre, mais au moins vous n'avez pas besoin de répéter le code.

0
LLL