Empresas
Empleos
  • Sobre nosotros
  • Soluciones
    • Publicación de vacantes
      Publica tu vacante y recibe candidatos calificados en 48h.
    • Evaluación de candidatos
      500+ pruebas técnicas y psicológicas, más anti-fraude.
    • Headhunting
      Búsqueda ejecutiva a la medida de principio a fin.
    • Nómina + EOR
      Dispersión de nómina y EOR en más de 15 países de LATAM.
  • Precios
  • Empleos

0

303
Vistas
*ngFor not updating, even with ChangeDetectorRef

I'm new to Angular, working with Angular 12 for a school assignment, trying to build a chat window of sorts that updates itself whenever the user sends a message, but I can't find a way to make it re-render when I add a new object to the array.

chat.component.ts:

@Component({
  selector: 'app-chat',
  templateUrl: './chat.component.html',
  styleUrls: ['./chat.component.scss']
})
@Injectable({  providedIn: 'root'  })
export class ChatComponent implements OnInit {
  messageArray: Array<any>;

  constructor(private changeDetector: ChangeDetectorRef) {
    this.messageArray = [{message: "test message 1", style: "answer"}];
  }
  ngOnInit(): void {}
  addMessage(message: string, style: string): void {
    this.messageArray = [...this.messageArray, {message: message, style: style}];
    this.changeDetector.detectChanges();
    console.log(this.messageArray);
  }

}

chat.component.html:

<div class="container chatContainer">
    <div class="row" *ngFor="let message of messageArray">
        <div class="col">
            <div class="text-wrap text-break message {{message.style}}">
                {{message.message}}
            </div>
        </div>
    </div>
</div>

I tried updating the array both with [...array] and with .push(), tried using [...array] to create a new array after pushing, tried both ChangeDetectionStrategy.Default and .OnPush, and tried doing all of those things also in the parent component that calls my addMessage() method. In all attempts, the array would log to the console correctly, but refuse to update the view.

Any ideas?

over 4 years ago · Santiago Trujillo
2 Respuestas
Responde la pregunta

0

If i were you, i would rather use a BehaviorSubject and do something like this:

@Component({
  selector: 'app-chat',
  templateUrl: './chat.component.html',
  styleUrls: ['./chat.component.scss']
})


@Injectable({  providedIn: 'root'  })
export class ChatComponent implements OnInit {
  messageArray: BehaviorSubect<Array<any>>;

  constructor(private changeDetector: ChangeDetectorRef) {
    this.messageArray = new BehaviorSubject<Array<any>>([{message: "test message 1", style: "answer"}]);
  }
  ngOnInit(): void {}
    addMessage(message: string, style: string): void {
    this.messageArray.next([...this.messageArray, {message: message, style: style}]);
  }
}

chat.component.html:

<div class="container chatContainer">
  <div class="row" *ngFor="let message of messageArray | async">
      <div class="col">
          <div class="text-wrap text-break message {{message.style}}">
              {{message.message}}
          </div>
      </div>
  </div>
</div>
over 4 years ago · Santiago Trujillo Denunciar

0

A colleague suggested I use @ViewChild to call the Chat component instead. So I removed the @Injectable from the Chat as zer0 suggested, and changed its parent Home component to this:

export class HomeComponent implements OnInit {

  @ViewChild(ChatComponent) private chatComponent: any;

  constructor(private cdr: ChangeDetectorRef) {
  }

  ngOnInit(): void {
  }

  onSend(): void {
    this.chatComponent.addMessage("test message", "question");
    this.cdr.detectChanges();
  }

}

Works now. Thanks!

Edit: a word

over 4 years ago · Santiago Trujillo Denunciar
Responde la pregunta
Encuentra empleos remotos

¡Descubre la nueva forma de encontrar empleo!

Top de empleos
Top categorías de empleo
Empresas
Publicar vacante Precios Comercial
Legal
Términos y condiciones Política de privacidad
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Recomiéndame algunas ofertas
Necesito ayuda