0👍
I think the issue is that you are drawing on top of the previous state because you are using ctx.restore()
and ctx.save()
wrapped around your canvas drawing logic. Try removing this and it should work. Also, you might want to put your logic in the afterDraw
callback (instead of beforeDraw
).
Also, here is another approach to implementing the same behavior but it uses custom tooltips instead. This is nice because it gives you way more flexibility to change the look and feel via html/css. Your approach is limited to understanding the canvas API to paint pixels.
Basically, you use an external custom tooltip positioned in the middle of the chart that is triggered when a chart segment is hovered.
Here is the relevant code
Chart.defaults.global.tooltips.custom = function(tooltip) {
// Tooltip Element
var tooltipEl = document.getElementById('chartjs-tooltip');
// Hide if no tooltip
if (tooltip.opacity === 0) {
tooltipEl.style.opacity = 0;
return;
}
// Set Text
if (tooltip.body) {
var total = 0;
// get the value of the datapoint
var value = this._data.datasets[tooltip.dataPoints[0].datasetIndex].data[tooltip.dataPoints[0].index].toLocaleString();
// calculate value of all datapoints
this._data.datasets[tooltip.dataPoints[0].datasetIndex].data.forEach(function(e) {
total += e;
});
// calculate percentage and set tooltip value
tooltipEl.innerHTML = '<h1>' + (value / total * 100) + '%</h1>';
}
// calculate position of tooltip
var centerX = (this._chartInstance.chartArea.left + this._chartInstance.chartArea.right) / 2;
var centerY = ((this._chartInstance.chartArea.top + this._chartInstance.chartArea.bottom) / 2);
// Display, position, and set styles for font
tooltipEl.style.opacity = 1;
tooltipEl.style.left = centerX + 'px';
tooltipEl.style.top = centerY + 'px';
tooltipEl.style.fontFamily = tooltip._fontFamily;
tooltipEl.style.fontSize = tooltip.fontSize;
tooltipEl.style.fontStyle = tooltip._fontStyle;
tooltipEl.style.padding = tooltip.yPadding + 'px ' + tooltip.xPadding + 'px';
};
And a working example as well.
- Chartjs-Get x.getPixelForValue(i) in a chartjs plugin with a time type scale
- Chartjs-Chart.js Barchart how to create legend item for bar?