user13976004
user13976004

Reputation:

Why template is not changed? - Angular

Template is:

  <tr *ngFor="let row of rows; let i = index">
     <div (click)=""edit(row)></div>
  </tr>

Component is:

 public edit(row: PostAddress): void {
      dialogRef.afterClosed().subscribe((postaddress) => {
            if (postaddress) {
                row = postaddress;
                 this._change.markForCheck();
            } 
 }

I see that variable was chnaged on a new value: row = postaddress; but template does not render.

I use changeDetection: ChangeDetectionStrategy.OnPush

Also I have tried this:

 row = postaddress;
 this._change.markForCheck();
 this._change.detectChanges();

Upvotes: 1

Views: 42

Answers (2)

Rafi Henig
Rafi Henig

Reputation: 6414

It has nothing to do with changeDetection, when assigning row = postaddress; the reference to the original row is lost, thus is not pointing to the one in the array any more, (row doesn't contain the row itself, rather a reference to it, when assigning to it a new object, it would hold a reference to the new object.)

public edit(row: PostAddress): void {
  dialogRef.afterClosed().subscribe((postaddress) => {
    if (postaddress)
    {
      rows.splice(rows.indexOf(row), 1, postaddress)
    }
  }

Or optionally using index provided by ngFor:

public edit(row: PostAddress, index : number): void {
  dialogRef.afterClosed().subscribe((postaddress) => {
   if (postaddress)
   {
    rows[index] = postaddress
   }
}

Upvotes: 1

Barremian
Barremian

Reputation: 31105

Instead of reassigning a element in the array, you could try to send the index and modify the element in the parent array. Try the following

Template

<tr *ngFor="let row of rows; let i = index">
  <div (click)="edit(index)></div>
</tr>

Controller

public edit(index): void {
  dialogRef.afterClosed().subscribe((postaddress) => {
    if (postaddress) {
      this.rows[i] = postaddress;     // <-- change item in the array
      this._change.markForCheck();
    }
  }); 
}

Upvotes: 1

Related Questions