Задать вопрос
@zlodiak

Почему subscribe() не видит nativeElement?

Пытаюсь динамически установить значения атрибутов для элемента шаблона:
<canvas id='graph' #graph *ngIf="trainings.length"></canvas>


В компоненте присвоение происходит в коллбеке ajax-запроса:
import { Component, OnInit, ViewChild, ElementRef } from '@angular/core';
import { TrainingsService } from '../../../services/trainings.service';
import { Training } from '../../../interfaces/training';

@Component({
  selector: 'app-graph',
  templateUrl: './graph.component.html',
  styleUrls: ['./graph.component.scss']
})
export class GraphComponent implements OnInit {

  private basicMeasure: number = 40;
  private trainings: Training[] = [];
  @ViewChild('graph') graph: ElementRef;
  constructor(private trainingsService: TrainingsService) { }

  ngOnInit() {
    this.getTrainings();
  }

  private getTrainings(): void {
    this.trainingsService.getTrainings().subscribe((trainings) => {
      this.trainings = trainings;
      const width = this.trainings.length * this.basicMeasure + 'px';
      const height = '260px';
      this.graph.nativeElement.style.width = width;
      this.graph.nativeElement.style.height = height;
      this.graph.nativeElement.style.backgroundColor = 'cyan';
    });
  }
}


В результате в консоли браузера получаю ошибку:
ERROR TypeError: Cannot read property 'nativeElement' of undefined


Но если присвоение выношу из коллбека, то всё работает без проблем:
ngOnInit() {
    this.getTrainings();

    setTimeout(() => {
      const width = this.trainings.length * this.basicMeasure + 'px';
      const height = '260px';
      this.graph.nativeElement.style.width = width;
      this.graph.nativeElement.style.height = height;
      this.graph.nativeElement.style.backgroundColor = 'cyan';
    }, 1000);
  }


Помогите пожалуйста разобраться почему такая несправедливость происходит?
  • Вопрос задан
  • 404 просмотра
Подписаться 1 Простой Комментировать
Решения вопроса 1
StivinKing
@StivinKing
Ваш graph еще не успевает появиться, а Вы уже пытаетесь к нему обратиться
Как вариант: пример
Ответ написан
Пригласить эксперта
Ответы на вопрос 1
search
@search
мама говорит что я особенный
Потому что на момент выполнения кода в subscribe(), элемента с id=graph еще не существует. *ngIf отрисует этот элемент не мгновенно после this.trainings = trainings, а только после выполнения функции subscribe().

Для того чтоб код не имел неприятного запаха из-за setTimeout(), можно передавать trainings в GraphComponent извне. Тогда это будет выглядеть как-то так:

<app-graph  [trainings]="trainings" *ngIf="trainings.length"></app-graph>
Ответ написан
Комментировать
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы