Hi I'm coming up to this error when trying to dynamically create some charts in my angular project.
Chart.js:9352 Failed to create chart: can't acquire context from the given item
export class StudentStudyProgressComponent implements OnInit {
charts = [];
semesters = [1, 2, 3, 4, 5, 6];
constructor(private logic: LogicService) {
}
ngOnInit() {
this.makeDetailCharts(this.semesters);
}
private makeDetailCharts(semesters: number[]) {
semesters.forEach((semester)=>{
this.charts.push(
new Chart('chartStudyProgress' + semester, {
type: 'doughnut',
data: {
labels: ['Geslaagd', 'Opgenomen', 'Resterend'],
datasets: [
{
data: this.logic.giveStudyProgressForSemester(this.student.Curriculum, semester),
borderColor: "#3cba9f",
backgroundColor: [
('#66B266'),
('#FFFF66'),
('#FF7F7F')
]
}
]
},
options: {
title: {
display: true,
text: 'Semester '+semester
},
legend: {
display: false
},
}
})
);
});
}
}
I think the problem occurs when I want to dynamically create the charts in my html:
<div class="row" *ngFor="let semester of semesters">
<div class="col-4">
<div [hidden]="!charts">
<canvas id="{{'chartStudyProgress'+semester}}" style="max-width: 30%;">{{ charts[semester] }}</canvas>
</div>
</div>
</div>
If I declare the charts statically it works:
<div class="row" >
<div class="col-4">
<div [hidden]="!charts">
<canvas id="chartStudyProgress1" style="max-width: 30%;">{{ charts[1] }}</canvas>
<canvas id="chartStudyProgress2" style="max-width: 30%;">{{ charts[2] }}</canvas>
<canvas id="chartStudyProgress3" style="max-width: 30%;">{{ charts[3] }}</canvas>
<canvas id="chartStudyProgress4" style="max-width: 30%;">{{ charts[4] }}</canvas>
<canvas id="chartStudyProgress5" style="max-width: 30%;">{{ charts[5] }}</canvas>
<canvas id="chartStudyProgress6" style="max-width: 30%;">{{ charts[6] }}</canvas>
</div>
</div>
</div>
Is there an expert who can help me create my charts dynamically?
You are trying to get canvases before they are created in the view. Use ngAfterViewInit
instead of ngOnInit
:
ngAfterViewInit() {
this.makeDetailCharts(this.semesters);
}