以角度4在一个组件与另一个组件之间共享数据

时间:2018-05-30 15:00:14

标签: angular angular5 angular2-forms

如何将父组件中的布尔值更改为子组件.ts  想要使用ngif显示和隐藏登录和注销选项但不工作。我不知道如何在两个组件之间设置和共享布尔值。我正在使用templateUrl。

app.component.ts:

export class AppComponent { 
public isValid:boolean;
constructor(private router:Router){ 
} 
 logout(){
 localStorage.removeItem('email');
 this.router.navigate(['./login']);
 this.isValid=true; 
 } 
 }

login.component.ts

export class LoginComponent implements OnInit {
public username:string;
public password:string; 
constructor(private router:Router) { } 
ngOnInit() {
} 
userLogin(form:NgForm){ 
if(form.value.username==="admin@gmail.com" && form.value.password==="admin")
 {
  localStorage.setItem('email',form.value.username);
  this.router.navigate(['./php']);
  this.isValid=false;//not working//
} }  }

app.component.html

<ul class="nav navbar-nav navbar-right">
  <li *ngIf="isValid">
    <a [routerLink]="['/login']" >Login</a>
  </li>

  <li *ngIf="!isValid">
      <a (click)="logout()">LogOut</a>
    </li>

</ul>

3 个答案:

答案 0 :(得分:1)

在缺少直接连接的组件(如兄弟姐妹,孙子等)之间传递数据时,您应该使用共享服务。 您可以使用RXJS BehaviorSubject Subject 进行跨组件通信。
Subject vs BehaviorSubject

创建服务

import { Injectable } from '@angular/core';
import { BehaviorSubject } from 'rxjs/BehaviorSubject';

    @Injectable()
    export class SharedService {

      private valueSource = new BehaviorSubject<boolean>(false);
      currentValue = this.valueSource.asObservable();

      constructor() { }

     changeValue(value: boolean) {
        this.valueSource.next(value)
      }

    }

使用Angular模块注册服务。

  

为什么呢?如果我们想要一个依赖的实例全局共享   在我们配置的应用程序上共享state   NgModule.

来自Angular docs

  

Angular模块提供程序(@NgModule.providers)已注册   应用程序的根注入器。 Angular可以注入相应的   它创建的任何类中的服务。一旦创建,就是一个服务实例   为应用程序的生命而活,Angular注入了这一项服务   每个需要它的类中的实例。

@NgModule({
      declarations: [
        AppComponent,


      ],
      imports: [

        BrowserModule,
        BrowserAnimationsModule,

      ],
      providers: [SharedService],
      bootstrap:[AppComponent],

在组件中注入SharedService
app.component.ts:

export class AppComponent { 
public isValid:boolean;
constructor(private router:Router:private service:SharedService){ 
       this.service.currentValue.subscribe(message => this.isValid = message);//subscribe to the currentValue observable.
} 
 logout(){
 localStorage.removeItem('email');
 this.router.navigate(['./login']);
 this.isValid=true;
 } 

login.component.ts

export class LoginComponent implements OnInit {
public username:string;
public password:string; 
public isValid:boolean;
constructor(private router:Router,private service:SharedService) {}


ngOnInit() {
} 
userLogin(form:NgForm){ 
if(form.value.username==="admin@gmail.com" && form.value.password==="admin")
 {
  localStorage.setItem('email',form.value.username);
  this.router.navigate(['./php']);
  this.isValid=false;
  this.service.changeValue(this.isValid);//it calls next on the BehaviorSubject to change its value.
} }  }

答案 1 :(得分:0)

我真的不明白什么是登录组件,因为它没有在提供的代码中的任何地方使用。无论如何,我强烈建议再次通过基础知识。您需要了解有关父子组件交互的更多信息。您可以在此处找到相关教程:https://angular.io/guide/component-interaction

答案 2 :(得分:0)

您必须使用@Input装饰器,您的代码几乎没问题,只需添加以下句子[isValid]="isLoginValid"@Input() isValid: any;

HTML应用组件

<child-component [isValid]="isLoginValid"><child-component>

<强> child.component.ts

Import {Input} from 'angular/core'

@Input() isValid: any;

....