How to display pie chart data values of each slice in chart.js
From what I know I don't believe that Chart.JS has any functionality to help for drawing text on a pie chart. But that doesn't mean you can't do it yourself in native JavaScript. I will give you an example on how to do that, below is the code for drawing text for each segment in the pie chart:
function drawSegmentValues()
{
for(var i=0; i<myPieChart.segments.length; i++)
{
// Default properties for text (size is scaled)
ctx.fillStyle="white";
var textSize = canvas.width/10;
ctx.font= textSize+"px Verdana";
// Get needed variables
var value = myPieChart.segments[i].value;
var startAngle = myPieChart.segments[i].startAngle;
var endAngle = myPieChart.segments[i].endAngle;
var middleAngle = startAngle + ((endAngle - startAngle)/2);
// Compute text location
var posX = (radius/2) * Math.cos(middleAngle) + midX;
var posY = (radius/2) * Math.sin(middleAngle) + midY;
// Text offside to middle of text
var w_offset = ctx.measureText(value).width/2;
var h_offset = textSize/4;
ctx.fillText(value, posX - w_offset, posY + h_offset);
}
}
A Pie Chart has an array of segments stored in PieChart.segments
, we can look at the startAngle
and endAngle
of these segments to determine the angle in between where the text would be middleAngle
. Then we would move in that direction by Radius/2
to be in the middle point of the chart in radians.
In the example above some other clean-up operations are done, due to the position of text drawn in fillText()
being the top right corner, we need to get some offset values to correct for that. And finally textSize
is determined based on the size of the chart itself, the larger the chart the larger the text.
Fiddle Example
With some slight modification you can change the discrete number values for a dataset into the percentile numbers in a graph. To do this get the total value
of the items in your dataset, call this totalValue
. Then on each segment you can find the percent by doing:
Math.round(myPieChart.segments[i].value/totalValue*100)+'%';
The section here myPieChart.segments[i].value/totalValue
is what calculates the percent that the segment takes up in the chart. For example if the current segment had a value of 50
and the totalValue was 200
. Then the percent that the segment took up would be: 50/200 => 0.25
. The rest is to make this look nice. 0.25*100 => 25
, then we add a %
at the end. For whole number percent tiles I rounded to the nearest integer, although can can lead to problems with accuracy. If we need more accuracy you can use .toFixed(n)
to save decimal places. For example we could do this to save a single decimal place when needed:
var value = myPieChart.segments[i].value/totalValue*100;
if(Math.round(value) !== value)
value = (myPieChart.segments[i].value/totalValue*100).toFixed(1);
value = value + '%';
Fiddle Example of percentile with decimals
Fiddle Example of percentile with integers
How to show slice value inside of slice in pie chart using chart.js
This answers the issue contained in the question's title:
How to show slice value inside of slice in pie chart using chart.js
The code snippet below show how to display the values inside the slices with the use of chartjs-plugin-labels
. The code of the samples was extracted from the chartjs-plugin-labels
demo page.
var canvas = document.getElementById('myChart');new Chart(canvas, { type: 'pie', data: { labels: ['January', 'February', 'March'], datasets: [{ data: [50445, 33655, 15900], backgroundColor: ['#FF6384', '#36A2EB','#FFCE56'] }] }, options: { responsive: true, maintainAspectRatio: true, plugins: { labels: { render: 'value', fontColor: ['green', 'white', 'red'] } } }});
<script src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.9.3/Chart.min.js"></script><script src="https://cdn.jsdelivr.net/gh/emn178/chartjs-plugin-labels/src/chartjs-plugin-labels.js"></script><canvas id="myChart"></canvas>
How add the sizes of the slices in the pie chart (at the top) in Chart.js?
I found the answer. My project is written in CoffeeScript, but I think it would be more useful for the StackOverflow community to post the code in JS.
options: {
legend: {
labels: {
generateLabels: function(chart) {
var data = chart.data;
if (data.labels.length && data.datasets.length) {
return data.labels.map(function(label, i) {
var meta = chart.getDatasetMeta(0);
var ds = data.datasets[0];
var arc = meta.data[i];
var custom = arc && arc.custom || {};
var getValueAtIndexOrDefault = Chart.helpers.getValueAtIndexOrDefault;
var arcOpts = chart.options.elements.arc;
var fill = custom.backgroundColor ? custom.backgroundColor : getValueAtIndexOrDefault(ds.backgroundColor, i, arcOpts.backgroundColor);
var stroke = custom.borderColor ? custom.borderColor : getValueAtIndexOrDefault(ds.borderColor, i, arcOpts.borderColor);
var bw = custom.borderWidth ? custom.borderWidth : getValueAtIndexOrDefault(ds.borderWidth, i, arcOpts.borderWidth);
var value = chart.config.data.datasets[arc._datasetIndex].data[arc._index];
return {
text: label + ": " + value,
fillStyle: fill,
strokeStyle: stroke,
lineWidth: bw,
hidden: isNaN(ds.data[i]) || meta.data[i].hidden,
index: i
};
});
} else {
return [];
}
}
}
}
}
Show values in Chart.js Pie chart parts
Yes, this is possible. You can achieve that using a Chart.js plugin called - Chart.PieceLabel.js.
Here is a basic example :
var chart = new Chart(ctx, { type: 'pie', data: { labels: ['Jan', 'Feb', 'Mar'], datasets: [{ data: [30, 40, 25], backgroundColor: 'rgba(0,119, 220, 0.2)' }] }, options: { pieceLabel: { render: 'value' //show values } }});
<script src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.7.0/Chart.min.js"></script><script src="https://cdn.rawgit.com/emn178/Chart.PieceLabel.js/master/build/Chart.PieceLabel.min.js"></script>
<canvas id="ctx"></canvas>
Displaying pie chart data value of each slices using react-chartjs-2
You can use this ChartJS Plugin - Chart.PieceLabel.js
first, install it via npm :
npm install chart.piecelabel.js --save
then, import it in your component :
import 'chart.piecelabel.js';
and finally, add the following in your chart options :
pieceLabel: {
render: 'value'
}
note: this is the minimum option needed to be set to display the value and you can find more options here.
ChartJS: datalabels: show percentage value in Pie piece
Updated fiddle with 2 decimal precision.
You were not computing the sum, instead storing the current value in sum only for every value.
Here is the working fiddle : https://jsfiddle.net/a1Lvn4eb/55/
var data = [{
data: [50, 55, 60, 33],
labels: ["India", "China", "US", "Canada"],
backgroundColor: [
"#4b77a9",
"#5f255f",
"#d21243",
"#B27200"
],
borderColor: "#fff"
}];
var options = {
tooltips: {
enabled: false
},
plugins: {
datalabels: {
formatter: (value, ctx) => {
let sum = 0;
let dataArr = ctx.chart.data.datasets[0].data;
dataArr.map(data => {
sum += data;
});
let percentage = (value*100 / sum).toFixed(2)+"%";
return percentage;
},
color: '#fff',
}
}
};
var ctx = document.getElementById("pie-chart").getContext('2d');
var myChart = new Chart(ctx, {
type: 'pie',
data: {
datasets: data
},
options: options
});
How to display data values on Chart.js
There is an official plugin for Chart.js 2.7.0+ to do this: Datalabels
Otherwise, you can loop through the points / bars onAnimationComplete and display the values
Preview
HTML
<canvas id="myChart1" height="300" width="500"></canvas>
<canvas id="myChart2" height="300" width="500"></canvas>
Script
var chartData = {
labels: ["January", "February", "March", "April", "May", "June"],
datasets: [
{
fillColor: "#79D1CF",
strokeColor: "#79D1CF",
data: [60, 80, 81, 56, 55, 40]
}
]
};
var ctx = document.getElementById("myChart1").getContext("2d");
var myLine = new Chart(ctx).Line(chartData, {
showTooltips: false,
onAnimationComplete: function () {
var ctx = this.chart.ctx;
ctx.font = this.scale.font;
ctx.fillStyle = this.scale.textColor
ctx.textAlign = "center";
ctx.textBaseline = "bottom";
this.datasets.forEach(function (dataset) {
dataset.points.forEach(function (points) {
ctx.fillText(points.value, points.x, points.y - 10);
});
})
}
});
var ctx = document.getElementById("myChart2").getContext("2d");
var myBar = new Chart(ctx).Bar(chartData, {
showTooltips: false,
onAnimationComplete: function () {
var ctx = this.chart.ctx;
ctx.font = this.scale.font;
ctx.fillStyle = this.scale.textColor
ctx.textAlign = "center";
ctx.textBaseline = "bottom";
this.datasets.forEach(function (dataset) {
dataset.bars.forEach(function (bar) {
ctx.fillText(bar.value, bar.x, bar.y - 5);
});
})
}
});
Fiddle - http://jsfiddle.net/uh9vw0ao/
Related Topics
What the Difference of This.State and This.Setstate in Reactjs
Optimum Way to Compare Strings in JavaScript
How to Solve 'Redirect Has Been Blocked by Cors Policy: No 'Access-Control-Allow-Origin' Header'
JavaScript - .Innerhtml Changes Auto Close Tags
Drawing Rotated Text on a HTML5 Canvas
D3Js Take Data from an Array Instead of a File
JavaScript - Dynamically Assign Onclick Event in the Loop
How to Load Images to User's Cache Asynchronously
Show Loading Icon Until the Page Is Load
How to Make a <Div> Move Up and Down When I'm Scrolling the Page
How to Get the Status Code from an Http Error in Axios
Javascript: Using a Condition in Switch Case
Can JavaScript Access Iframe Elements from the Parent Page
How to Bind the HTML <Title> Content in Vuejs
How to Abort Image <Img> Load Requests Without Using Window.Stop()