2016-03-02 33 views
13

Come un componente può modificare una variabile su un altro componente. Esempio:Angolare 2 variabili componente variabili su un altro componente

Ho un componente app.component.ts

@Component({ 
    selector: 'my-app', 
    template: ` 
    <nav *ngIf="onMain == false"> 
     Hello 
    </nav> 
    ` 
}) 

export class AppComponent{ 
    onMain: Boolean; 

    constructor(){ 
     this.onMain = false; 
    } 
} 

ho un altro componente che voglio cambiare onMain nel mio componente app main.component.ts

import {AppComponent} from '../app.component'; 

@Component({ 
    selector: 'main-app', 
    template: `` 
}) 

export class MainComponent{ 

    constructor() { 
     this.appComponent = AppComponent; 
     this.appComponent.onMain = true; 
    } 
} 

Mi aspetterei che Ciao scomparirebbe, ma non lo fa. Come posso avere un componente cambiare il valore su un altro componente?

+0

È possibile utilizzare 'EventEmitter' in un servizio ** **. Quindi consentire ad AppComponent di iscriversi per ottenere l'evento della modifica. –

risposta

13

Prima di tutto, non si ha il collegamento tra due componenti o forse qualcosa non è corretto nel codice. Se hai uno scenario genitore/figlio puoi usare @Input,@Output di angular2. Se non si dispone di uno scenario genitore/figlio, è possibile utilizzare EventEmitter,SharedService di angular2.

Working demo-EventEmitter way

ho considerato AppComponent è un parentComponent e MainComponent come un componente figlio. Utilizzando i concetti SharedService & EventEmitter di angular2, sono in grado di nascondere la parte di visualizzazione AppComponent's facendo clic su un pulsante che appartiene alla vista "MainComponent".

AppComponent.ts

import {Component,bind,CORE_DIRECTIVES,OnInit} from 'angular2/core'; 
import {MainComponent} from 'src/MainComponent'; 
import {SharedService} from 'src/shared.service'; 
@Component({ 
    selector: 'my-app', 
    directives:[MainComponent], 
    template: `<h1>AppComponent {{onMain}}</h1> 
    <div *ngIf="onMain == false"> 
     Hello 
     <br> __________________________________<br> 
    </div> 

    <main-app></main-app> 
    ` 
}) 

export class AppComponent implements OnInit { 
    onMain: Boolean; 

    constructor(ss: SharedService) { 
     this.onMain = false; 
     this.ss = ss; 
    } 



    ngOnInit() { 
    this.subscription = this.ss.getEmittedValue() 
     .subscribe(item => this.onMain=item); 
    } 

} 

MainComponent.ts

import {Component,bind,CORE_DIRECTIVES} from 'angular2/core'; 
import {SharedService} from 'src/shared.service'; 
@Component({ 
    selector: 'main-app', 

    template: `<h1> MainComponent</h1> 
    <button (click)="changeName()">Change Name</button> 
    ` 
}) 

export class MainComponent { 



    constructor(ss: SharedService) { 
     this.ss = ss; 
    } 

    changeName() { 
     this.ss.change(); 
    } 
} 

shared.service.ts

import {Component, Injectable,Input,Output,EventEmitter} from 'angular2/core' 


@Injectable() 
export class SharedService { 
    @Output() fire: EventEmitter<any> = new EventEmitter(); 

    constructor() { 
    console.log('shared service started'); 
    } 

    change() { 
    console.log('change started'); 
    this.fire.emit(true); 
    } 

    getEmittedValue() { 
    return this.fire; 
    } 

} 
+0

Da dove proviene questa.scrizione su AppComponent? Sto ricevendo un errore che l'abbonamento di proprietà non esiste su AppComponent – ClickThisNick

+0

Hai aggiunto il file ** 'rx.js' **? guarda il ** index.html' ** nella mia demo plunker. troverai i riferimenti necessari per i file richiesti. E se le risposte sono adatte alle tue esigenze, dovresti accettarle come risposta, in modo che altre possano riferirsi ad essa come una risposta. – micronyks

+0

@micronyks grazie. Puoi condividere anche il pacchetto.json? Perché le cose non funzionano con l'ultima piattaforma e altri pacchetti per favore. –

1

Sì, è possibile modificare il valore della variabile da un componente a un altro per questo è necessario inject la classe del componente esportato nel componente genitore così facendo si è in grado di raggiungere ogni metodo e variabile della classe iniettato (componente).

import {Component} from 'angular2/core'; 
@Component({ 
    selector: 'my-app', 
    templateUrl: `myTemplate.html`, 
    directive: [AppComponent2] 
}) 

export class AppComponent { 
    variable1: boolean = true; 
} 

@Component({ 
    selector: 'my-app2', 
    templateUrl: `temp2.html`, 
    providers: [AppComponent] 
}) 

export class AppComponent2 { 
    constructor(private appComponent: AppComponent){ } 
    Fun(){ 
    console.log('Function Called'); 
    this.appComponent.variable1 = false; 
    } 
} 


<button (click)='Fun()'>Change Variable</button> 

{{appComponent.variable1}} 

Esempio di lavoro http://plnkr.co/edit/fpYFueOnkm5sa4JfG7uX?p=preview

6

Se non v'è alcuna relazione tra i componenti (intendo genitore/figlio), è necessario utilizzare un servizio condiviso con una proprietà EventEmitter. Un componente emetterà un evento basato su di esso e questo altro componente riceverà una notifica sottoscrivendo lo EventEmitter. Quando si riceve l'evento, questo componente può impostare una proprietà utilizzata per mostrare/nascondere il pulsante ...

  • servizio condiviso

    @Injectable() 
    export class SharedService { 
        onMainEvent: EventEmitter = new EventEmitter(); 
    } 
    

    Non dimenticare di definire il corrispondente provider nel boostrap funzione per poter condividere la stessa istanza del servizio per l'intera applicazione: `bootstrap (AppComponent, [SharedService]);

  • AppComponent componente

    @Component({ ... }) 
    export class AppComponent { 
        onMain: boolean = false; 
        constructor(service: MenuService) { 
        sharedService.onMainEvent.subscribe(
         (onMain) => { 
         this.onMain = onMain; 
         } 
        ); 
    } 
    

    }

  • MainComponent componente:

    export class MainComponent { 
        constructor(private service: SharedService) { 
        } 
    
        updateOnMain(onMain):void { 
        this.service.onMainEvent.emit(onMain); 
        } 
    } 
    

Queste domande per maggiori dettagli:

0

Se hai una relazione genitore/figlio puoi usare un emettitore di eventi per capovolgere la variabile con solo un paio di linee di codice. Non è necessario scrivere un intero servizio condiviso.

app.component.ts

@Component({ 
    selector: 'my-app', 
    template: ` 
    <nav *ngIf="onMain == false" (observableEvent)="onMain == true"> 
     Hello 
    </nav> 
    ` 
}) 

main.component.ts

import {AppComponent} from '../app.component'; 
import { Output, EventEmitter } from '@angular/core'; 

@Component({ 
    selector: 'main-app', 
    template: `` 
}) 

export class MainComponent{ 
    @Output() observableEvent: EventEmitter<any> = new EventEmitter<any>(); 

    constructor() { 
     this.appComponent = AppComponent; 
     this.observableEvent.emit(); 
    } 
} 
Problemi correlati