Actualmente estoy usando Angular 2. Usualmente usamos @Output() addTab = new EventEmitter<any>();y luego addTab.emit()para emitir un evento al componente principal.
¿Hay alguna forma de hacerlo viceversa, de padres a hijos?
Actualmente estoy usando Angular 2. Usualmente usamos @Output() addTab = new EventEmitter<any>();y luego addTab.emit()para emitir un evento al componente principal.
¿Hay alguna forma de hacerlo viceversa, de padres a hijos?
Respuestas:
Usando RxJs , puede declarar un Subjecten su componente principal y pasarlo como Observablecomponente secundario, el componente secundario solo necesita suscribirse a esto Observable.
Componente principal
eventsSubject: Subject<void> = new Subject<void>();
emitEventToChild() {
this.eventsSubject.next();
}
HTML principal
<child [events]="eventsSubject.asObservable()"> </child>
Componente hijo
private eventsSubscription: Subscription;
@Input() events: Observable<void>;
ngOnInit(){
this.eventsSubscription = this.events.subscribe(() => doSomething());
}
ngOnDestroy() {
this.eventsSubscription.unsubscribe();
}
this.eventsSubject.next({data});en el padre, luego this.events.subscribe(({data}) => doSomething(data));en el hijo.
eventsSubjecta un Observable en lugar de simplemente suscribirse a él como un Sujeto?
Hasta donde yo sé, hay 2 formas estándar de hacerlo.
1. @Input
Siempre que los datos en el padre cambian, el niño recibe una notificación sobre esto en el método ngOnChanges. El niño puede actuar en consecuencia. Esta es la forma estándar de interactuar con un niño.
Parent-Component
public inputToChild: Object;
Parent-HTML
<child [data]="inputToChild"> </child>
Child-Component: @Input() data;
ngOnChanges(changes: { [property: string]: SimpleChange }){
// Extract changes to the input property by its name
let change: SimpleChange = changes['data'];
// Whenever the data in the parent changes, this method gets triggered. You
// can act on the changes here. You will have both the previous value and the
// current value here.
}
Creando un servicio y usando un observable en el servicio compartido. El niño se suscribe y siempre que haya un cambio, se notificará al niño. Este también es un método popular. Cuando desee enviar algo diferente a los datos que pasa como entrada, se puede utilizar.
SharedService
subject: Subject<Object>;
Parent-Component
constructor(sharedService: SharedService)
this.sharedService.subject.next(data);
Child-Component
constructor(sharedService: SharedService)
this.sharedService.subject.subscribe((data)=>{
// Whenever the parent emits using the next method, you can receive the data
in here and act on it.})
<child [data]="inputToChild"> </child>probablemente debería ser <child [data]="(inputToChild)"> </child>para obtener cambios
En un componente principal, puede usar @ViewChild () para acceder al método / variable del componente secundario.
@Component({
selector: 'app-number-parent',
templateUrl: './number-parent.component.html'
})
export class NumberParentComponent {
@ViewChild(NumberComponent)
private numberComponent: NumberComponent;
increase() {
this.numberComponent.increaseByOne();
}
decrease() {
this.numberComponent.decreaseByOne();
}
}
Actualizar:
Angular 8 en adelante -
@ViewChild(NumberComponent, { static: false })
numberComponentserá undefined.
Utilice el decorador @Input () en su componente hijo para permitir que el padre se vincule a esta entrada.
En el componente hijo, lo declaras como está:
@Input() myInputName: myType
Para vincular una propiedad de padre a hijo, debe agregar en su plantilla los corchetes de enlace y el nombre de su entrada entre ellos.
Ejemplo:
<my-child-component [myChildInputName]="myParentVar"></my-child-component>
Pero tenga cuidado, los objetos se pasan como referencia, por lo que si el objeto se actualiza en el hijo, la var del padre se actualizará demasiado. Esto podría dar lugar a algún comportamiento no deseado en algún momento. Con los tipos primarios se copia el valor.
Para ir más lejos, lea esto:
Documentos: https://angular.io/docs/ts/latest/cookbook/component-communication.html
Dentro del padre, puede hacer referencia al hijo usando @ViewChild. Cuando sea necesario (es decir, cuando se disparará el evento), puede ejecutar un método en el hijo del padre utilizando la referencia @ViewChild.