Angular8 ngFor子数据绑定不呈现

Posted

技术标签:

【中文标题】Angular8 ngFor子数据绑定不呈现【英文标题】:Angular8 ngFor Child Data Binding Not Rendering 【发布时间】:2020-03-08 00:46:04 【问题描述】:

我对 Angular 并不陌生,我希望这段代码能够呈现父级提供的数据(也许 Angular8 改变了语法)。也许我对此很陌生。具体的问题是为什么在父 ngFor 循环中列出的具有数据绑定的子组件没有呈现列表中的数据。

console.logs 显示数组。

子组件有一个被渲染的复选框;不呈现人名、状态和部门。我遵循了这些确切的步骤:https://www.youtube.com/watch?v=FGStS1hD5Y4 这是代码:

parent.component.html:

<div>Json results:</div>
<table>
  <tr>
    <th></th>
    <th>Name</th>
    <th>Status</th>
    <th>Department</th>
  </tr>
  <tr>
    <td>
      <app-people
        *ngFor="let person of people"
        [personItem]="person"
      ></app-people>
    </td>
  </tr>
</table>

<router-outlet></router-outlet>

parent.component.ts:

import  Component  from '@angular/core';
import  HttpClient  from '@angular/common/http';
import  PeopleService  from './people.service';
import  People  from './people';

@Component(
  selector: 'app-root',
  templateUrl: './app.component.html',
  styleUrls: ['./app.component.css']
)
export class AppComponent 
  people = [];
  avatars = [];
  constructor(private peopleService: PeopleService, private http: HttpClient) 
    this.http
      .get(`assets/people.json`)
      .toPromise()
      .then(data => 
        console.log(data);

        for (let key in data)
          if (data.hasOwnProperty(key)) this.people.push(data[key]);
      );

    this.http
      .get(`assets/avatars.json`)
      .toPromise()
      .then(data => 
        console.log(data);

        for (let key in data)
          if (data.hasOwnProperty(key)) this.avatars.push(data[key]);
      );
  

child.component.html:

<div class="people-container">
  <input
    type="checkbox"
    [checked]="person.isSelected"
    (change)="complete.emit($event.target.checked)"
  />
  <span [ngClass]=" selected: person.isSelected " class="person-title">
    <table>
      <tr>
        <ng-container *ngFor="let img of avatars">
          <td *ngIf="personItem.id == img.id"><img [src]="img.avatar" /></td>
        </ng-container>
        <td> personItem.name </td>
        <td> personItem.status </td>
        <td> personItem.department </td>
      </tr>
    </table>
  </span>

  <button (click)="remove.emit(person.id)">X</button>
</div>

child.component.ts:

import 
  Component,
  OnInit,
  Input,
  Output,
  EventEmitter,
  ChangeDetectionStrategy
 from "@angular/core";
import  People  from "../people";
@Component(
  selector: "app-people",
  templateUrl: "./people.component.html",
  styleUrls: ["./people.component.css"],
  changeDetection: ChangeDetectionStrategy.OnPush
)
export class PeopleComponent implements OnInit 
  people = [];
  avatars = [];
  @Input() personItem: People;
  @Output() select = new EventEmitter<boolean>();
  @Output() remove = new EventEmitter<number>();

  constructor() 

  ngOnInit() 

如果还有什么需要请询问。

【问题讨论】:

分享 People ts 文件 你的代码应该没问题,检查你的模型属性名称用户在赋值和html中绑定的语法是否正确。 它可能没有被渲染的原因可能是由于*ngIf指令中的条件是false。我还可以看到您正在 AppComponent 中调用 get 请求并存储数组,但尚未将其传递给您在 *ngFor 中迭代它的子组件。 @user3875919 我相信该数组的目的是使用 [personItem] = person 的数据绑定在父项中传递,然后在子项中使用 personItem.name 等。既然这不起作用,我怎么能把数组给孩子呢?它必须保留在 ngFor 循环的父组件中。当我将数组添加到父组件和子组件时,console.log 光线会为每个数组项输出一次。 @kamprasad- 我认为你是对的,而且我在 People 模型中的合同与我在子组件中调用属性的方式相匹配。我没有看到导致数据无法呈现的问题,并且它编译时没有错误。缺少什么? 【参考方案1】:

您的子组件正在使用 OnPush 策略,这意味着每次输入更改时它都不会更新组件。要解决这个问题,只需添加一个 OnChanges 生命周期,在构造函数中注入 ChangeDetectionRef 并在 OnChanges 中触发它。

@Component(
  selector: "app-people",
  templateUrl: "./people.component.html",
  styleUrls: ["./people.component.css"],
  changeDetection: ChangeDetectionStrategy.OnPush
)
export class PeopleComponent implements OnInit, OnChanges 
  people = [];
  avatars = [];
  @Input() personItem: People;
  @Output() select = new EventEmitter<boolean>();
  @Output() remove = new EventEmitter<number>();

  constructor(private cdr: ChangeDetectionRef) 

  ngOnInit() 

  ngOnChanges()  
    this.cdr.detectChanges();
  

或者您可以删除 changeDetection: ChangeDetectionStrategy.OnPush 行,一切都会正常。

【讨论】:

“'ChangeDetectionStrategy' 类型上不存在属性 'detectChanges'”。 你必须注入 ChangeDetectionRef,而不是 ChangeDetectionStrategy 我在子组件导入中添加了 ChangeDetectorRef 并实现了这一点,但子数据中仍然没有响应。 好的,你删除 changeDetection: ChangeDetectionStrategy.OnPush 行? 是的,有没有试过。我认为发生了一些奇怪的事情。

以上是关于Angular8 ngFor子数据绑定不呈现的主要内容,如果未能解决你的问题,请参考以下文章

在 Angular 8 中使用 *ngFor 索引从数组中渲染特定项目

如何以角度将数据与ngFor绑定

如何将 Angular 5 中的点击数据从父组件传递到子组件?

ngFor 无法通过与 @Input 的组件绑定来迭代另一个组件

*ngFor 在 <li> 中使用 Angular 版本 8.2.8 绑定从 API 接收的数据,但无法显示数据

dpdk网卡绑定和解绑