Example on Plunker.
I have 2 1 issues, when there are 3 or more slices in the pie, it looks like there is a little sliver that is not filled in. The other is if there are less than 3 slices in the pie, it looks all wonky.
Looks like the wonky happens when a slice is over 50% of the pie (StephenH comment below).
This is the bit of code that fills in the slices based on an array $scope.viewData
is a simple array, [1,2,3]
for example. The $scope.viewDataTotal
variable is the sum of the array values, 6
for the shown example array.
$scope.updateView = function () {
if ($scope.viewData) {
var svg = $element.children('svg');
svg.empty();
var cX = $element.width() / 2;
var cY = $element.height() / 2;
var r = cX;
if (cY < r) {
r = cY;
}
r -= 5;
if (r < 0) {
r = 0;
}
var sd = 0;
var idxColor = 0;
$scope.viewData.forEach(function(i) {
var degrees = i / $scope.viewDataTotal * 360;
var p = '<path d="';
p += generateWedgeString(cX, cY, sd, sd + degrees, r);
p += '" fill="';
p += $scope.colors[idxColor];
p +='" stroke="none" stroke-width="0" />';
svg.append(jQuery(p));
sd += degrees;
idxColor++;
});
$element.html($element.html());
}
};
The math bit is in the generateWedgeString
function:
var generateWedgeString = function(startX, startY, startAngle, endAngle, radius){
var x1 = startX + radius * Math.cos(Math.PI * startAngle/180);
var y1 = startY + radius * Math.sin(Math.PI * startAngle/180);
var x2 = startX + radius * Math.cos(Math.PI * endAngle/180);
var y2 = startY + radius * Math.sin(Math.PI * endAngle/180);
var pathString = "M"+ startX + "," + startY + " L" + x1 + "," + y1 + " A" + radius + "," + radius + " 0 0,1 " + x2 + "," + y2 + " z";
return pathString;
};
update:
Dave's answer works but it introduces other issues. For example You can see the divider between each 1/2 of the slice. Another would be I can't easily do mouse over events.