score:9
getElementsAtEvent
checks only the main elements of the chart (bars, points, sectors...). If you want to consider labels too, you'll have to reimplement the functionality for labels.
Most of the code you need is already available in different methods in the Chart.js library code. Just copy-paste / cleanup as done below.
Script
Your click hander should be
$('#myChart').click(function (e) {
var helpers = Chart.helpers;
var eventPosition = helpers.getRelativePosition(e, myRadarChart.chart);
var mouseX = eventPosition.x;
var mouseY = eventPosition.y;
var activePoints = [];
// loop through all the labels
helpers.each(myRadarChart.scale.ticks, function (label, index) {
for (var i = this.getValueCount() - 1; i >= 0; i--) {
// here we effectively get the bounding box for each label
var pointLabelPosition = this.getPointPosition(i, this.getDistanceFromCenterForValue(this.options.reverse ? this.min : this.max) + 5);
var pointLabelFontSize = helpers.getValueOrDefault(this.options.pointLabels.fontSize, Chart.defaults.global.defaultFontSize);
var pointLabeFontStyle = helpers.getValueOrDefault(this.options.pointLabels.fontStyle, Chart.defaults.global.defaultFontStyle);
var pointLabeFontFamily = helpers.getValueOrDefault(this.options.pointLabels.fontFamily, Chart.defaults.global.defaultFontFamily);
var pointLabeFont = helpers.fontString(pointLabelFontSize, pointLabeFontStyle, pointLabeFontFamily);
ctx.font = pointLabeFont;
var labelsCount = this.pointLabels.length,
halfLabelsCount = this.pointLabels.length / 2,
quarterLabelsCount = halfLabelsCount / 2,
upperHalf = (i < quarterLabelsCount || i > labelsCount - quarterLabelsCount),
exactQuarter = (i === quarterLabelsCount || i === labelsCount - quarterLabelsCount);
var width = ctx.measureText(this.pointLabels[i]).width;
var height = pointLabelFontSize;
var x, y;
if (i === 0 || i === halfLabelsCount)
x = pointLabelPosition.x - width / 2;
else if (i < halfLabelsCount)
x = pointLabelPosition.x;
else
x = pointLabelPosition.x - width;
if (exactQuarter)
y = pointLabelPosition.y - height / 2;
else if (upperHalf)
y = pointLabelPosition.y - height;
else
y = pointLabelPosition.y
// check if the click was within the bounding box
if ((mouseY >= y && mouseY <= y + height) && (mouseX >= x && mouseX <= x + width))
activePoints.push({ index: i, label: this.pointLabels[i] });
}
}, myRadarChart.scale);
var firstPoint = activePoints[0];
if (firstPoint !== undefined) {
alert(firstPoint.index + ': ' + firstPoint.label);
}
});
Fiddle - http://jsfiddle.net/1Lngmtz7/
score:1
I came up with a solution for this for version 2.8.0 by copying the label position calculations from the RadialLinear scale into an event handler.
document.getElementById("myChart").onclick = function (e) {
var helpers = Chart.helpers;
var scale = myRadarChart.scale;
var opts = scale.options;
var tickOpts = opts.ticks;
// Position of click relative to canvas.
var mouseX = e.offsetX;
var mouseY = e.offsetY;
var labelPadding = 5; // number pixels to expand label bounding box by
// get the label render position
// calcs taken from drawPointLabels() in scale.radialLinear.js
var tickBackdropHeight = (tickOpts.display && opts.display) ?
helpers.valueOrDefault(tickOpts.fontSize, Chart.defaults.global.defaultFontSize)
+ 5: 0;
var outerDistance = scale.getDistanceFromCenterForValue(opts.ticks.reverse ? scale.min : scale.max);
for (var i = 0; i < scale.pointLabels.length; i++) {
// Extra spacing for top value due to axis labels
var extra = (i === 0 ? tickBackdropHeight / 2 : 0);
var pointLabelPosition = scale.getPointPosition(i, outerDistance + extra + 5);
// get label size info.
// TODO fix width=0 calc in Brave?
// https://github.com/brave/brave-browser/issues/1738
var plSize = scale._pointLabelSizes[i];
// get label textAlign info
var angleRadians = scale.getIndexAngle(i);
var angle = helpers.toDegrees(angleRadians);
var textAlign = 'right';
if (angle == 0 || angle == 180) {
textAlign = 'center';
} else if (angle < 180) {
textAlign = 'left';
}
// get label vertical offset info
// also from drawPointLabels() calcs
var verticalTextOffset = 0;
if (angle === 90 || angle === 270) {
verticalTextOffset = plSize.h / 2;
} else if (angle > 270 || angle < 90) {
verticalTextOffset = plSize.h;
}
// Calculate bounding box based on textAlign
var labelTop = pointLabelPosition.y - verticalTextOffset - labelPadding;
var labelHeight = 2*labelPadding + plSize.h;
var labelBottom = labelTop + labelHeight;
var labelWidth = plSize.w + 2*labelPadding;
var labelLeft;
switch (textAlign) {
case 'center':
var labelLeft = pointLabelPosition.x - labelWidth/2;
break;
case 'left':
var labelLeft = pointLabelPosition.x - labelPadding;
break;
case 'right':
var labelLeft = pointLabelPosition.x - labelWidth + labelPadding;
break;
default:
console.log('ERROR: unknown textAlign '+textAlign);
}
var labelRight = labelLeft + labelWidth;
// Render a rectangle for testing purposes
ctx.save();
ctx.strokeStyle = 'red';
ctx.lineWidth = 1;
ctx.strokeRect(labelLeft, labelTop, labelWidth, labelHeight);
ctx.restore();
// compare to the current click
if (mouseX >= labelLeft && mouseX <= labelRight && mouseY <= labelBottom && mouseY >= labelTop) {
alert(scale.pointLabels[i]+' clicked');
// Break loop to prevent multiple clicks, if they overlap we take the first one.
break;
}
}
};
JSFiddle here:
https://jsfiddle.net/simoncoggins/7r08uLk9/
The downside of this approach is it that it will break if the core labelling implementation changes in the future. It would be better if the library separated the calculation of label position from its rendering and started exposing the position info via the API. Then this solution could be greatly simplified and would be more robust to library changes.
I've opened a ticket offering to make that change here:
https://github.com/chartjs/Chart.js/issues/6549
Please comment on that issue if it would be useful to you.
score:1
Cannot read property 'getDatasetMeta' of undefined Chartjs
If you got this error from doc example of chartjs, the client is the problem. Replace it with the client of your current instance.
In my case im using myHorizontalBar
var defaultLegendClickHandler = function(e, legendItem) {
var index = legendItem.datasetIndex;
var ci = window.myHorizontalBar; //this.chart;
var meta = ci.getDatasetMeta(index);
// See controller.isDatasetVisible comment
meta.hidden = meta.hidden === null ? !ci.data.datasets[index].hidden : null;
// We hid a dataset ... rerender the chart
ci.update();
}
window.onload = function() {
var ctx = document.getElementById('canvas').getContext('2d');
window.myHorizontalBar = new Chart(ctx, {
type: 'horizontalBar',
data: horizontalBarChartData,
options: {
score:12
in chart.js 2.5 (maybe even earlier) you can put an onClick in the options:
'legend' : {
'onClick' : function (evt, item) {
console.log ('legend onClick', evt, item);
},
'display' : true,
'labels' : ...
Source: stackoverflow.com
Related Query
- How to add OnClick Event on labels in Chart.js v2.0?
- How to add an on click event to my Line chart using Chart.js
- How to add images to chart labels with vue-chartjs?
- How to add labels on top of the chart bar with Chart.js 2
- How to add on click event to chart js
- How to add data labels in each bar in stacked bar chart in chart.js?
- How to add text inside the doughnut chart using Chart.js?
- How to add labels into Chart.js canvas plugin?
- Chart.js how to show cursor pointer for labels & legends in line chart
- How to display Line Chart dataset point labels with Chart.js?
- How to add images as labels to Canvas Charts using chart.js
- How to add an offset to a dataset in Chart js
- How to add second Y-axis for Bar and Line chart in Chart.js?
- How to add text in centre of the doughnut chart using Chart.js?
- How to add datas to chart js from javascript array itself?
- How to add panning to chart in chartjs?
- How to display data labels outside in pie chart with lines in ionic
- How to align Chart.JS line chart labels to the center
- How to access labels array using chart plugin (Chart.pluginService.register) in Chartjs 2.x?
- How to display the labels in doughnut chart using ng2 charts?
- How to add a second set of labels to a Chart.js doughnut chart?
- how to add a title to my ng2-charts bar chart
- Chart.js Radar Chart How to Remove Outer Labels
- How to get onClick Event for a Label in ChartJS and React?
- How to add comma in this chart js
- How to add gradient background to Line Chart [vue-chart.js]
- How can I add some text in the middle of a half doughnut chart in Chart.JS?
- How to add ChartJS code in Html2Pdf to view image
- How to draw a needle on a custom donut chart and add datapoints to the needle?
- ChartJs - Pie Chart - how to remove labels that are on the pie chart
More Query from same tag
- Chart.js in flex element overflows instead of shrinking
- Format Tooltip Chartjs TypeScript Angular
- How can I hide tooltip in Chart.js on a specific data label?
- How can I get chart.js to automatically add colours for dynamic labels?
- How do I change pointBackgroundColor in Line segment on ChartJS?
- Chart.js <frame> or <iframe> elements do not have a title
- How to add gradient background to Line Chart [vue-chart.js]
- Increase space between legend and chart
- ChartJs line chart - display permanent icon above some data points with text on hover
- Adding reading off lines in ChartJS
- Chart.js - if there is not value show 0
- chart.js - dynamically added chart makes previous ones disappear
- How to parse "hh:mm:ss" strings to time in Charts.js 3.x
- Chart Js, Style some ticks on the axis differently
- Chart.js 3.3.0 - Draw text on top of chart
- Rendering a chart.js component twice in a page
- How do I import Chart.js Helper Functions in Django?
- ChartJS/High Charts Radar chart - Different radial axis labels for each category that appear on hover
- how to transform changing data to be visualized in a chart.js
- Chart js loading screen
- Loop Dataset ChartJS Javascript
- Remove the vertical line in the chart js line chart
- Highlight date in Chart.js line graph
- Create a arc like doughnut chart with Chart js plugins
- How to init elements after data is loaded?
- Update the chart data from an array stored in a variable on button click
- how to display chart.js legend with different bar color
- Chart.js wrong x axis date time?
- ChartJS - handling of overlapping points in line chart
- How to have solid colored bars in angular-chart bar chart