更改来自不同组件的变量值 - Angular 4

时间:2018-05-28 17:10:42

标签: html angular eventemitter

我有两个组件,一个是home.component,另一个是loading.component(加载屏幕)。加载屏幕倒计时,倒数后,他做了一些事情。我需要做的是使加载屏幕具有自定义倒计时长度。 我尝试使用EventEmiter,但它没有用。

home.component.html:

<a (click)="applyChanges()" class="green" style="margin-left: 8px; cursor: pointer"><i style="margin-right: 5px;"class="fa fa-check"></i>Apply changes now</a>

home.component.ts

@Output() loadingScreenStart: EventEmitter<any> = new EventEmitter();


applyChanges(){
this.dashboard.applyChanges().catch(
  err => {
    console.log("There was an error: "+err.status);
    console.log("There was an error: "+err.statusText);
    //this.handleError(err);
    return Observable.throw(err);
  }
)
.subscribe(
  data => {
    this.loadingScreenStart.emit(34);
    this.router.navigate(['/loading']);
  }
);

} loading.component.html

<div class="container container-table" (loadingScreenStarted)="onScreenStart($event)">
  <div class="row vertical-10p">
    <div class="container">
      <img src="../../assets/img/LoginLogo.png" class="center-block logo">
      <img style="width: 15em"  src="../../assets/img/gears.svg" class="center-block ">
      <div class="text-center col-sm-6 col-sm-offset-3">
        <h1>Changes are taking place</h1>
        <h4>You will be redirected in {{timeLeft}} seconds</h4>
      </div>
    </div>
  </div>

loading.component.ts

import { Component, OnInit, Input } from '@angular/core';
import { AuthGuard } from '../guard/auth.guard';
import { Title } from '@angular/platform-browser';
@Component({
  selector: 'app-loading',
  templateUrl: './loading.component.html',
  styleUrls: ['./loading.component.css']
})
export class LoadingComponent implements OnInit {
   public timeLeft;
   public intervalId;
   constructor(public titleService: Title, public guard: AuthGuard) { }
   onScreenStart(length) {
      this.timeLeft = length;
      console.log(length);
   }
   ngOnInit() {
      this.titleService.setTitle("Loading... | something);
      this.startCounter();
      localStorage.removeItem('statusInfo');
   }
   startCounter() {
      this.intervalId = setInterval(() => {
         if (this.timeLeft == 1) {
            clearInterval(this.interValId);
         }
         this.timeLeft--;
      }, 1000)
   }
}

2 个答案:

答案 0 :(得分:0)

你的代码有两个问题。

  1. 了解EventEmitter的工作原理。
  2. 当您使用eventEmitter从child发出值时,您需要将其映射到父组件的某个方法。

    // in child component.
        @Output()
        myEmitter   = new EventEmitter();
    
        someMethod() {
         this.myemitter.emit('somevalue');
    }
    

    现在它实际上接收到此值的发射器,您需要将其映射到父组件的方法。

      someParentMethod(value) {
          console.log(value);
      }
    
    <app-child (myEmitter)="someParentMethod(event)"></app-child>
    

    2。 Observable的错误处理。 因为你抛出一个Observable,你需要在订阅中处理它。 Observable的订阅包含3个部分。 响应 ErrorHandling 下一步。现在,你从Observable.throw抛出一个错误,你的res部分将无法运行。但是你没有处理错误,所以你什么都看不到。而是这样做:

    .subscribe(
      data => {
        this.loadingScreenStart.emit(34);
        this.router.navigate(['/loading']);
      },
      error => console.log(error)
    );
    

答案 1 :(得分:0)

由于这两个组件不属于父/子关系,因此我不认为您将能够成功使用EventEmitter。主要问题是你不能同时依赖两个组件。

因此,您的情况的两个常见选择是:

  1. 传递路线参数中的数据(例如https://angular.io/tutorial/toh-pt5#navigating-to-hero-details

  2. 通过共享服务进行通信(例如https://angular.io/guide/component-interaction#parent-and-children-communicate-via-a-service