Angular 2 @ViewChild 不起作用。无法读取未定义的属性“标题”

2024-02-07

即使使用 @ViewChild 导入后,我也无法访问组件的属性。下面是代码。

header.monitor.component.ts

import { AdminComponent } from 'admin/admin.component';
import { Component } from '@angular/core';
import { ViewChild, AfterViewInit } from '@angular/core';

@Component({
    selector: 'monitor-header',
    templateUrl: './header.monitor.component.html',
    styleUrls: ['./header.monitor.component.css']
})

export class HeaderMonitorComponent implements AfterViewInit {

    @ViewChild(AdminComponent) private admin: AdminComponent;

    private monitorTitle: string;

    ngAfterViewInit() {
        this.monitorTitle = this.admin.title;
    }
 }

header.monitor.component.html

<div class="text-center header h3">{{monitorTitle}}</div>

管理组件.ts

import { Component, OnInit, ViewChild } from '@angular/core';
import { ElementRef } from '@angular/core';

@Component({
  selector: 'monitor-admin',
  templateUrl: './admin.component.html',
  styleUrls: ['./admin.component.css']
})
export class AdminComponent {

  constructor() { }

  title = 'Header';

}

错误错误:未捕获(承诺中):TypeError:无法读取未定义的属性“标题” 类型错误:无法读取未定义的属性“标题”

帮我解决这个错误。


您应该检查@ViewChild in the AfterViewChecked而不是AfterViewInit。您还可以捆绑您的@angular/core像这样导入:import { Component, ViewChild, AfterViewInit } from '@angular/core';。然后而不是实施AfterViewInit只是实施AfterViewChecked.

它看起来是这样的:

import { AdminComponent } from 'admin/admin.component';
import { Component, ViewChild, AfterViewChecked } from '@angular/core';

@Component({
    selector: 'monitor-header',
    templateUrl: './header.monitor.component.html',
    styleUrls: ['./header.monitor.component.css']
})

export class HeaderMonitorComponent implements AfterViewChecked {

    @ViewChild(AdminComponent) private admin: AdminComponent;

    private monitorTitle: string;

    ngAfterViewChecked() {
        this.monitorTitle = this.admin.title;
    }
 }

一个问题:这两个组件都是父组件还是其中一个组件是另一个组件的子组件?我问的原因是您可能想研究一种在组件之间传递该变量的不同方法,因为这可以通过@Input或使用服务来存储和设置标头变量。我希望这能有所帮助。

EDIT:

要回答您的评论,您应该创建如下服务:

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

@Injectable()
export class HeaderService {

  _title: string;

  constructor() { }

  set title(title) {
    this._title = title;
  }
  get title() {
    return this._title;
  }

}

然后在您的组件中导入服务并get or set变量:

import { AdminComponent } from 'admin/admin.component';
import { Component, ViewChild, AfterViewChecked } from '@angular/core';
import { HeaderService } from 'path/to/your/service';

@Component({
    selector: 'monitor-header',
    templateUrl: './header.monitor.component.html',
    styleUrls: ['./header.monitor.component.css']
})

export class HeaderMonitorComponent implements AfterViewChecked {

    @ViewChild(AdminComponent) private admin: AdminComponent;

    private monitorTitle: string;

    constructor(private headerService: HeaderService) {} // Import service here


    ngAfterViewChecked() {
        this.monitorTitle = this.headerService.title;
    }
 }

您只需要确保使用以下命令在其中一个组件中设置标题this.headerService.title = 'yourTitle';

我只是不确定首先加载哪个组件。

您应该在这里查看 Angular 服务:https://angular.io/tutorial/toh-pt4 https://angular.io/tutorial/toh-pt4

另请查看此处的 Angular 组件交互:https://angular.io/guide/component-interaction https://angular.io/guide/component-interaction

EDIT #2:

这是在您的服务中订阅该标题的另一种方法:

所以下面我创建了一个Subject它是字符串类型,并且这里有一个方法告诉它是下一个要保存和发送的字符串。

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

@Injectable()
export class HeaderService {

  public titleSubject: Subject<string> = new Subject<string>();

  constructor() { }

  setNextTitle(title) {
    this.titleSubject.next();
  }

}

然后在你的HeaderMonitorComponent你想订阅那个Subject像这样:

import { AdminComponent } from 'admin/admin.component';
import { Component, OnInit ViewChild, AfterViewChecked } from '@angular/core';
import { Observable } from 'rxjs/Observable';
import { HeaderService } from 'path/to/your/service';

@Component({
    selector: 'monitor-header',
    templateUrl: './header.monitor.component.html',
    styleUrls: ['./header.monitor.component.css']
})

export class HeaderMonitorComponent implements OnInit, AfterViewChecked {

    @ViewChild(AdminComponent) private admin: AdminComponent;

    private monitorTitle: string;
    titleObservable: Observable<string>;

    constructor(private headerService: HeaderService) {} // Import service here

    ngOnInit() {

       this.titleObservable = this.headerService.titleSubject.asObservable();
       this.titleObservable.subscribe((title) => {
          this.monitorTitle = title;
       });
    }

    ngAfterViewChecked() {
        this.monitorTitle = this.headerService.title;
    }
 }

然后在你的AdminComponent,每当单击按钮时,调用this.headerService.setNextTitle(title)然后您在 HeaderMonitorComponent 中订阅的新标题将被确认并替换当前值monitorTitle.

这只是处理数据传递的另一种快速方法。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Angular 2 @ViewChild 不起作用。无法读取未定义的属性“标题” 的相关文章

随机推荐