web-dev-qa-db-fra.com

L'enfant écoute l'événement parent dans Angular 2

Dans angular docs, il y a un sujet sur l'écoute d'événements parent pour les enfants. C'est bien. Mais mon but est quelque chose d'inverser!! Vue de la page d’administration (menu de la barre latérale, barre des tâches, état, etc.) Dans ce composant parent, j’ai configuré le système du routeur pour changer la vue principale entre les autres pages de l’administrateur. bouton dans la barre des tâches (qui est placé dans admin.component) et le composant enfant doit écouter cet événement de clic pour pouvoir sauvegarder le personnel.

64
Hamed Hamedi

Je pense que ce document pourrait vous être utile:

En fait, vous pouvez exploiter un sujet observable/que le parent fournit à ses enfants. Quelque chose comme ca:

@Component({
  (...)
  template: `
    <child [parentSubject]="parentSubject"></child>
  `,
  directives: [ ChildComponent ]
})
export class ParentComponent {
  parentSubject:Subject<any> = new Subject();

  notifyChildren() {
    this.parentSubject.next('some value');
  }
}

Le composant enfant peut simplement s'abonner sur ce sujet:

@Component({
  (...)
})
export class ChildComponent {
  @Input()
  parentSubject:Subject<any>;

  ngOnInit() {
    this.parentSubject.subscribe(event => {
      // called when the notifyChildren method is
      // called in the parent component
    });
  }

  ngOnDestroy() {
    // needed if child gets re-created (eg on some model changes)
    // note that subsequent subscriptions on the same subject will fail
    // so the parent has to re-create parentSubject on changes
    this.parentSubject.unsubscribe();
  }

}

Sinon, vous pourriez exploiter un service partagé contenant un tel sujet de manière similaire ...

85
Thierry Templier

Pour la postérité, je pensais mentionner la solution la plus conventionnelle: Obtenez simplement une référence à ViewChild, puis appelez directement l'une de ses méthodes.

@Component({
  selector: 'app-child'
})
export class ChildComponent {

  notifyMe() {
    console.log('Event Fired');
  }
}

@Component({
  selector: 'app-parent',
  template: `<app-child #child></app-child>`
})
export class ParentComponent {

  @ViewChild('child')
  private child: ChildComponent;

  ngOnInit() {
    this.child.notifyMe();
  }
}
105
Stephen Paul

Une approche plus simple pourrait être possible ici si je comprends bien la question. Hypothèses --

  • OP a un bouton de sauvegarde dans le composant parent
  • Les données à sauvegarder sont dans les composants enfants
  • Toutes les autres données dont le composant enfant pourrait avoir besoin sont accessibles depuis les services.

Dans le composant parent

<button type="button" (click)="prop1=!prop1">Save Button</button>
<app-child-component [setProp]='prop1'></app-child-component>

Et chez l'enfant ..

prop1:boolean;
  @Input()
  set setProp(p: boolean) {
    // -- perform save function here
}

Cela envoie simplement le clic du bouton au composant enfant. À partir de là, le composant enfant peut enregistrer les données indépendamment.

EDIT: si les données du modèle parent doivent également être transmises avec le clic du bouton, cette approche est également possible. Faites-moi savoir si c'est le cas et je mettrai à jour les exemples de code.

9
charsi