web-dev-qa-db-fra.com

Événement à déclencher lorsqu'une instruction angular * ngIf est évaluée dans le modèle

Si j'ai les éléments suivants:

<div *ngIf="user$ | async as user" class="container">
   <p>{{user.name}}</p>
</div>

Existe-t-il un moyen d'exécuter du code lorsque le div ci-dessus apparaît enfin à l'écran?

13
Sammy

Le ngIf supprimera cet élément DOM et tous les composants/directives attachés. Vous pouvez donc simplement écrire une simple directive qui exécute un événement lors de sa création. Lorsque le ngIf passe de false à true, la directive sera créée (encore et encore, etc ...)

@Directive({selector: '[after-if]'})
export class AfterIfDirective implements AfterContentInit {
    @Output('after-if')
    public after: EventEmitter<AfterIfDirective> = new EventEmitter();

    public ngAfterContentInit(): void {
        setTimeout(()=>{
           // timeout helps prevent unexpected change errors
           this.after.next(this);
        });
    }
}

Exemple HTML:

<div *ngIf="user$ | async as user" class="container" (after-if)="your expression">
    <p>user.name</p>
</div>
13
Reactgular

Une solution sans création d'une nouvelle directive consiste à prendre un avant de @ViewChild comportement:

Décorateur de propriété qui configure une requête de vue. Le détecteur de changement recherche le premier élément ou la directive correspondant au sélecteur dans la vue DOM. Si la vue DOM change et qu'un nouvel enfant correspond au sélecteur, la propriété est mise à jour.

La partie importante est Si la vue DOM change ce qui signifie que dans ce cas, cela ne se déclenchera que lorsque le l'élément est créé ou détruit.

Déclarez d'abord un nom de variable pour l'élément, pour l'exemple que j'ai utilisé #userContent

    <div #userContent *ngIf="user$ | async as user" class="container">
      <p>user.name</p>
    </div>

Ajoutez ensuite un @ViewChild référence à l'intérieur de votre composant:

    @ViewChild('userContent') set userContent(element) {
      if (element) {
         // here you get access only when element is rendered (or destroyed)
      }
    }

Cette solution a été fournie à l'intérieur ne autre question , également @ViewChild le détail du comportement est disponible ici .

2
Luis Limas