Estoy usando @input
para recibir una propiedad del componente principal para activar una clase CSS en uno de los elementos del componente secundario.
Puedo recibir la propiedad de los padres y también activar la clase. Pero esto funciona solo una vez. La propiedad que estoy recibiendo de los padres es un dato booleano escrito y cuando establezco el estado de la misma en false
el componente secundario, no cambia en los padres.
Plunkr: https://plnkr.co/edit/58xuZ1uzvToPhPtOING2?p=preview
app.ts
import {Component, NgModule} from '@angular/core'
import {BrowserModule} from '@angular/platform-browser'
import { HeaderComponent } from './header';
import { SearchComponent } from './header/search';
@Component({
selector: 'my-app',
template: `
<app-header></app-header>
`,
})
export class App {
name:string;
constructor() {
}
}
@NgModule({
imports: [ BrowserModule ],
declarations: [ App, HeaderComponent, SearchComponent ],
bootstrap: [ App ]
})
export class AppModule {}
header.ts
import { Component, OnInit } from '@angular/core';
@Component({
selector: 'app-header',
template: `<header>
<app-search [getSearchStatus]="isSearchActive"></app-search>
<button (click)="handleSearch()">Open Search</button>
</header>`
})
export class HeaderComponent implements OnInit {
isSearchActive = false;
handleSearch() {
this.isSearchActive = true
console.log(this.isSearchActive)
}
constructor() { }
ngOnInit() { }
}
header / search.ts
import { Component, OnInit, Input } from '@angular/core';
@Component({
selector: 'app-search',
template: `<div id="search" [class.toggled]="getSearchStatus">
search
<button (click)="getSearchStatus = false" class="close">Close Search</button>
</div>`
})
export class SearchComponent implements OnInit {
@Input() getSearchStatus: boolean;
constructor() { }
ngOnInit() {
}
}
Por favor revise el plunker dado arriba. La función de búsqueda abierta solo funciona una vez. Después de cerrar la búsqueda, no vuelve a dispararse.
¿ @input
Es el caso de uso adecuado para este escenario? Por favor ayúdame a arreglar esto. (Actualice el plunker).
fuente
true
enhandleSearch()
?Respuestas:
Necesita utilizar enlace de datos bidireccional.
@Input()
es un enlace de datos de una forma. para habilitar el enlace de datos bidireccional, debe agregar un@Output()
correspondiente a la propiedad, con un sufijo "Cambiar"@Input() getSearchStatus: boolean; @Output() getSearchStatusChange = new EventEmitter<boolean>();
cuando desee publicar el cambio realizado en su propiedad al padre, debe notificar al padre con:
this.getSearchStatusChange.emit(newValue)
y en el padre necesita usar la notación banana-in-a-box para esa propiedad:
también puede vincularse a la propiedad y activar una devolución de llamada cuando cambia en child:
ver el plnkr
fuente
@Output()
. Eso suena a reinventar la rueda. @RobertVangorpublic
, no pude usar el enfoque de "caja banana" y obtuve errores de que no era una propiedad conocida del componente ... Sin(propertyChanged)="setParentProp($event)"
embargo, la vinculación solo con el funcionó perfectamente.Otro enfoque: use rxjs / BehaviorSubject para pasar el estado entre diferentes componentes.
Aquí está el plunkr .
Nombre el asunto con un sufijo 'Rxx', por lo que el BehaviorSubject para searchStatus será searchStatusRxx.
searchStatusRxx = new BehaviorSubject(false);
,searchStatusRxx.next(value)
debe cambiar el último valor.fuente
Editó su código un poco, funciona y parece más simple en mi opinión. Dime si te gusta.
https://plnkr.co/edit/oJOjEZfAfx8iKZmzB3NY?p=preview
fuente
Otra forma más. Plunkr . Lo que queremos es una única fuente de verdad. Podemos poner eso en niño esta vez.
searchStatus = false
#as
o cualquier nombre.#as.searchStatus
y en childthis.searchStatus
.fuente